using ExcelDataReader;
using System;
using System.Collections.Generic;
using System.Data;
using System.Data.SqlTypes;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace arinc_1553_CSharpGUI
{
    class ReadExcel
    {
        /* define constants */
        public const ushort EXCEL_SHEET_GENERAL = 0;
        public const ushort EXCEL_SHEET_1553MESSAGES = 1;
        public const ushort EXCEL_SHEET_1553PARAMETERS = 2;
        public const ushort EXCEL_SHEET_1553FRAMES_CHAN1 = 3;
        public const ushort EXCEL_SHEET_1553FRAMES_CHAN2 = 4;
        public const ushort EXCEL_SHEET_ARINCMESSAGES = 5;
        public const ushort EXCEL_SHEET_ARINCPARAMETERS = 6;
        public const ushort EXCEL_SHEET_CODEDTYPES = 7;

        public const byte NUM_1553_CHANNELS = 2;

        IExcelDataReader excelReader;
        DataSet dsresult;

        //MajorFrame pFrame = new MajorFrame();

        //List<MsgArinc429> pArincMsgs = new List<MsgArinc429>();

        MajorFrame[] pFrame;

        List<MsgArinc429> pArincMsgs;

        string m_fileName;

        public ReadExcel(string fileName, ref MajorFrame[] majFrame, ref List<MsgArinc429> arincMsgs)
        {
            pFrame = majFrame;
            pArincMsgs = arincMsgs;
            m_fileName = fileName;
        }

        public bool InitExcelRead()
        {
            //string filePath = "C:\\Users\\Subhashini BS\\Projects\\drht-24123-gui\\Source\\ARINC_1553_CSharpGUI\\DRHT-24123-GUI-Sample-Config-File.xlsx";
            FileStream stream;

            try
            {
                stream = File.Open(m_fileName, FileMode.Open, FileAccess.Read);
            }
            catch (Exception)
            {
                MessageBox.Show("Error opening Config file.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                return false;
            }

            //1. Reading Excel file
            if (Path.GetExtension(m_fileName).ToUpper() == ".XLS")
            {
                //1.1 Reading from a binary Excel file ('97-2003 format; *.xls)
                excelReader = ExcelReaderFactory.CreateBinaryReader(stream);
            }
            else
            {
                //1.2 Reading from a OpenXml Excel file (2007 format; *.xlsx)
                excelReader = ExcelReaderFactory.CreateOpenXmlReader(stream);
            }

            //2. DataSet - The result of each spreadsheet will be created in the result.Tables
            //DataSet result = excelReader.AsDataSet();

            //3. DataSet - Create column names from first row
            //excelReader.IsFirstRowAsColumnNames = false;

            dsresult = excelReader.AsDataSet(new ExcelDataSetConfiguration()
            {
                ConfigureDataTable = (_) => new ExcelDataTableConfiguration()
                {
                    UseHeaderRow = false
                }
            });

            return true;
        }

        public void DeInitExcelRead()
        {
            //5. Free resources (IExcelDataReader is IDisposable)
            excelReader.Close();
        }

        public bool ReadGeneralSheetFromExcel(/*ref MajorFrame majFrame*/out string LRU_Part_No, out string LRU_Serial_No)
        {
            DataTable dt = dsresult.Tables[EXCEL_SHEET_GENERAL];
            LRU_Part_No = LRU_Serial_No = "";

            pFrame[0].retryType = dt.Rows[1][0].ToString().Trim();
            if ((pFrame[0].retryType != "Once_on_Same_Bus") &&
                (pFrame[0].retryType != "Once_on_Alt_Bus") &&
                (pFrame[0].retryType != "1st_2nd_on_Same_Bus") &&
                (pFrame[0].retryType != "1st_2nd_on_Alt_Bus") &&
                (pFrame[0].retryType != "1st_on_Same_Bus-2nd_on_Alt_Bus") &&
                (pFrame[0].retryType != "1st_on_Alt_Bus-2nd_on_Same_Bus"))
            {
                MessageBox.Show("In \"General\" sheet, RETRY_TYPE is invalid. Valid values are:" +
                                        "\nOnce_on_Same_Bus\nOnce_on_Alt_Bus\n1st_2nd_on_Same_Bus\n1st_2nd_on_Alt_Bus\n1st_on_Same_Bus-2nd_on_Alt_Bus\n1st_on_Alt_Bus-2nd_on_Same_Bus",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                return false;
            }

            try
            {
                pFrame[0].minorFramePeriod = UInt16.Parse(dt.Rows[1][1].ToString());

                /*if (!(pfrmStruct.period >= 0 && pfrmStruct.period <= 15))
                {
                    MessageBox.Show("In \"Frames\" sheet, minor frame period in row " + (rowNo + 1).ToString() + " and column 1 is not between 0 and 15.",
                                    "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }*/
            }
            catch (Exception)
            {
                MessageBox.Show("In \"General\" sheet, minor frame period is invalid.",
                                    "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                return false;
            }

            pFrame[1].retryType = pFrame[0].retryType;
            pFrame[1].minorFramePeriod = pFrame[0].minorFramePeriod;

            LRU_Part_No = dt.Rows[1][2].ToString().Trim();

            LRU_Serial_No = dt.Rows[1][3].ToString().Trim();

            return true;
        }

        /**
        * @brief This function reads the "1553-Messages" worksheet of excel config file and populates
        *          the msgList member variable.
        * @return true if successful, false otherwise.
        */
        public bool Read1553MessageListFromExcel(/*ref MajorFrame majFrame*/)
        {
            int rowNo;
            string tempStr;
            List<string> msgNames = new List<string>();
            bool syncAMsgFound = false;

            /* Read all messages from the "Messages" sheet */

            int numOfRows = dsresult.Tables[EXCEL_SHEET_1553MESSAGES].Rows.Count;
            DataTable dt = dsresult.Tables[EXCEL_SHEET_1553MESSAGES];

            for (rowNo = 1; rowNo < numOfRows; rowNo++)
            {
                Msg1553 newMsg = new Msg1553();

                newMsg.name = dt.Rows[rowNo][0].ToString().Trim();

                // remove leading and trailing whitespaces
                newMsg.name = newMsg.name.Trim();

                if (newMsg.name.Length == 0)  // Ignore if the line is junk
                {
                    continue;
                }

                if (newMsg.name.StartsWith("//"))  // Ignore if the line is commented
                {
                    continue;
                }

                if (newMsg.name.Contains(' '))  // Message name should not have space inbetween
                {
                    MessageBox.Show("In \"Messages\" sheet, message name \"" + newMsg.name + "\" in row " + (rowNo+1).ToString() + " and column 1 contains space inbetween.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }

                msgNames.Add(newMsg.name);
                // Check for duplicate message name
                for (int ctr = 0; ctr < msgNames.Count - 1; ctr++)
                {
                    if (newMsg.name == msgNames[ctr])
                    {
                        MessageBox.Show("In \"Messages\" sheet, message name \"" + newMsg.name + "\" in row " + (rowNo + 1).ToString() + " and column 1 is duplicate.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }
                }

                if (newMsg.name == "SYNC_A")
                {
                    syncAMsgFound = true;
                }

                newMsg.type = dt.Rows[rowNo][1].ToString().Trim();
                if ((newMsg.type != "BC --> RT") &&
                    (newMsg.type != "RT --> BC") &&
                    (newMsg.type != "RT --> RT") &&
                    (newMsg.type != "MODE"))
                {
                    MessageBox.Show("In \"Messages\" sheet, MSG_TYPE in row " + (rowNo + 1).ToString() + " and column 2 is invalid. Valid values are:\nBC --> RT\nRT --> BC\nRT --> RT\nMODE",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }

                try
                {
                    newMsg.rtAddr1 = UInt16.Parse(dt.Rows[rowNo][2].ToString());

                    if (!(newMsg.rtAddr1 >= 0 && newMsg.rtAddr1 <= 31))
                    {
                        MessageBox.Show("In \"Messages\" sheet, RT Address 1 value in row " + (rowNo + 1).ToString() + " and column 3 is not between 0 and 31.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }

                    if ((newMsg.name == "SYNC_A" || newMsg.name == "SYNC_B") && newMsg.rtAddr1 != 31)
                    {
                        MessageBox.Show("In \"Messages\" sheet, RT Address 1 value in row " + (rowNo + 1).ToString() + " and column 3 for SYNC_A/SYNC_B message should be 31.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }
                }
                catch (Exception)
                {
                    MessageBox.Show("In \"Messages\" sheet, RT Address 1 value in row " + (rowNo + 1).ToString() + " and column 3 is invalid.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }

                try
                {
                    newMsg.sa1 = UInt16.Parse(dt.Rows[rowNo][3].ToString());

                    if (newMsg.type == "MODE")
                    {
                        if (!(newMsg.sa1 == 0 || newMsg.sa1 == 31))
                        {
                            MessageBox.Show("In \"Messages\" sheet, Sub address 1 should be 0 or 31 in row " + (rowNo + 1).ToString() + " and column 4.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }
                    }
                    else if (!(newMsg.sa1 >= 0 && newMsg.sa1 <= 31))
                    {
                        MessageBox.Show("In \"Messages\" sheet, Sub address 1 value in row " + (rowNo + 1).ToString() + " and column 4 should be between 0 and 31.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }
                }
                catch (Exception)
                {
                    MessageBox.Show("In \"Messages\" sheet, Sub address 1 value in row " + (rowNo + 1).ToString() + " and column 4 is invalid.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }

                try
                {
                    newMsg.wordCount_ModeCode = UInt16.Parse(dt.Rows[rowNo][4].ToString());

                    if (!(newMsg.wordCount_ModeCode >= 1 && newMsg.wordCount_ModeCode <= 32))
                    {
                        MessageBox.Show("In \"Messages\" sheet, value of WC_MC in row " + (rowNo + 1).ToString() + " and column 5 should be between 1 and 32.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }

                    if (newMsg.wordCount_ModeCode == 32)
                    {
                        newMsg.wordCount_ModeCode = 0;
                    }

                    if ((newMsg.name == "SYNC_A" || newMsg.name == "SYNC_B") && newMsg.wordCount_ModeCode != 17)
                    {
                        MessageBox.Show("In \"Messages\" sheet, value of WC_MC in row " + (rowNo + 1).ToString() + " and column 5 for SYNC_A/SYNC_B message should be 17.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }
                }
                catch (Exception)
                {
                    MessageBox.Show("In \"Messages\" sheet, value of WC_MC in row " + (rowNo + 1).ToString() + " and column 5 is invalid.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }

                if (dt.Rows[rowNo][5].ToString().Length != 0)
                {
                    try
                    {
                        newMsg.rtAddr2 = UInt16.Parse(dt.Rows[rowNo][5].ToString());

                        if (!(newMsg.rtAddr2 >= 0 && newMsg.rtAddr2 <= 31))
                        {
                            MessageBox.Show("In \"Messages\" sheet, RT Address 2 value in row " + (rowNo + 1).ToString() + " and column 6 is not between 0 and 31.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }
                    }
                    catch (Exception)
                    {
                        MessageBox.Show("In \"Messages\" sheet, RT Address 2 value in row " + (rowNo + 1).ToString() + " and column 6 is invalid.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }
                }
                else
                {
                    newMsg.rtAddr2 = 65535;
                }

                if (dt.Rows[rowNo][6].ToString().Length != 0)
                {
                    try
                    {
                        newMsg.sa2 = UInt16.Parse(dt.Rows[rowNo][6].ToString());

                        if (!(newMsg.sa2 >= 0 && newMsg.sa2 <= 31))
                        {
                            MessageBox.Show("In \"Messages\" sheet, Sub Address 2 value in row " + (rowNo + 1).ToString() + " and column 7 should be between 0 and 31.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }
                    }
                    catch (Exception)
                    {
                        MessageBox.Show("In \"Messages\" sheet, Sub Address 2 value in row " + (rowNo + 1).ToString() + " and column 7 is invalid.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }
                }
                else
                {
                    newMsg.sa2 = 65535;
                }

                newMsg.bus = dt.Rows[rowNo][7].ToString().Trim();
                if ((newMsg.bus != "BUS_A") &&
                    (newMsg.bus != "BUS_B"))
                {
                    MessageBox.Show("In \"Messages\" sheet, BUS in row " + (rowNo + 1).ToString() + " and column 8 is invalid. Valid values are:\nBUS_A\nBUS_B",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }
                if (newMsg.name == "SYNC_A" && newMsg.bus != "BUS_A")
                {
                    MessageBox.Show("In \"Messages\" sheet, value of BUS in row " + (rowNo + 1).ToString() + " and column 8 for SYNC_A message should be BUS_A",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }
                if (newMsg.name == "SYNC_B" && newMsg.bus != "BUS_B")
                {
                    MessageBox.Show("In \"Messages\" sheet, value of BUS in row " + (rowNo + 1).ToString() + " and column 8 for SYNC_B message should be BUS_B",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }

                tempStr = dt.Rows[rowNo][8].ToString().Trim(); // retryEnabled
                if ((tempStr != "YES") &&
                    (tempStr != "NO") &&
                    (tempStr != ""))
                {
                    MessageBox.Show("In \"Messages\" sheet, RETRY_ENABLED in row " + (rowNo + 1).ToString() + " and column 9 is invalid. Valid values are:\nYES\nNO\nBlank value",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }
                newMsg.retryEnabled = (tempStr == "YES" ? true : false);

                newMsg.channel = dt.Rows[rowNo][9].ToString().Trim();
                if ((newMsg.channel != "1") &&
                    (newMsg.channel != "2") &&
                    (newMsg.channel != "Both"))
                {
                    MessageBox.Show("In \"Messages\" sheet, channel in row " + (rowNo + 1).ToString() + " and column 10 is invalid. Valid values are:\n1\n2\nBoth",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }

                //newMsg.retryType = dt.Rows[rowNo][9].ToString().Trim();
                //if ((newMsg.retryType != "Once_on_Same_Bus") &&
                //    (newMsg.retryType != "Once_on_Alt_Bus") &&
                //    (newMsg.retryType != "1st_2nd_on_Same_Bus") &&
                //    (newMsg.retryType != "1st_2nd_on_Alt_Bus") &&
                //    (newMsg.retryType != "1st_on_Same_Bus-2nd_on_Alt_Bus") &&
                //    (newMsg.retryType != "1st_on_Alt_Bus-2nd_on_Same_Bus"))
                //{
                //    MessageBox.Show("In \"Messages\" sheet, RETRY_TYPE in row " + (rowNo + 1).ToString() + " and column 10 is invalid. Valid values are:" +
                //                            "\nOnce_on_Same_Bus\nOnce_on_Alt_Bus\n1st_2nd_on_Same_Bus\n1st_2nd_on_Alt_Bus\n1st_on_Same_Bus-2nd_on_Alt_Bus\n1st_on_Alt_Bus-2nd_on_Same_Bus",
                //                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                //    return false;
                //}

                newMsg.cw1 = (ushort) ((newMsg.rtAddr1 << 11) + (newMsg.sa1 << 5) + newMsg.wordCount_ModeCode);
                if (newMsg.type == "RT --> BC")
                {
                    newMsg.cw1 += 0x400;   /* Set direction bit to 1 for RT->BC messages */
                }

                if (newMsg.type == "RT --> RT")
                {
                    newMsg.cw2 = (ushort)((newMsg.rtAddr2 << 11) + 0x400 + (newMsg.sa2 << 5) + newMsg.wordCount_ModeCode);
                }

                for (int ctr = 0; ctr < 32; ctr++)
                {
                    newMsg.wordInfo[ctr].wordName = "";
                    newMsg.wordInfo[ctr].numOfParameters = 0;
                }

                /*                for (int index = 0, colNo = 15; index < 32; index++, colNo++) // doubt
                                {
                                    newMsg.wordInfo[index].wordName = messageSheet->read(rowNo, colNo).toString();
                                }*/

                if (newMsg.channel == "1")
                {
                    pFrame[0].msgs.Add(newMsg);
                }
                else if (newMsg.channel == "2")
                {
                    pFrame[1].msgs.Add(newMsg);
                }
                else
                {
                    pFrame[0].msgs.Add(newMsg);

                    Msg1553 newMsg2 = new Msg1553();

                    newMsg2.name = newMsg.name;
                    newMsg2.type = newMsg.type;
                    newMsg2.rtAddr1 = newMsg.rtAddr1;
                    newMsg2.sa1 = newMsg.sa1;
                    newMsg2.wordCount_ModeCode = newMsg.wordCount_ModeCode;
                    newMsg2.rtAddr2 = newMsg.rtAddr2;
                    newMsg2.sa2 = newMsg.sa2;
                    newMsg2.bus = newMsg.bus;
                    newMsg2.retryEnabled = newMsg.retryEnabled;
                    newMsg2.channel = newMsg.channel;
                    newMsg2.cw1 = newMsg.cw1;
                    newMsg2.cw2 = newMsg.cw2;

                    for (int ctr = 0; ctr < 32; ctr++)
                    {
                        newMsg2.wordInfo[ctr].wordName = "";
                        newMsg2.wordInfo[ctr].numOfParameters = 0;
                    }

                    pFrame[1].msgs.Add(newMsg2);
                }
            }

#if SYNC_MSG_MANDATORY
        if(syncAMsgFound == false)
        {
            MessageBox.Show("In \"Messages\" sheet, message name \"SYNC_A\" is not found.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
            return false;
        }
#endif

            return true;
        }

        /**
         * @brief This function reads the "Coded-Types" sheet of ETSM config file and populates
         *          "m_CodedTypes" from this information.
         * @return true if successful, false otherwise.
         */
        public bool ReadCodedTypesFromExcel(ref List<CodedType> m_CodedTypes)
        {
            int numOfColumns = dsresult.Tables[EXCEL_SHEET_CODEDTYPES].Columns.Count;
            int numOfRows = dsresult.Tables[EXCEL_SHEET_CODEDTYPES].Rows.Count;
            DataTable dt = dsresult.Tables[EXCEL_SHEET_CODEDTYPES];

            for (int colNo = 0; colNo < numOfColumns; colNo++)
            {
                string codedTyp = dt.Rows[0][colNo].ToString().Trim();

                if (codedTyp.Length != 0)
                {
                    CodedType codedTypes = new CodedType();

                    codedTypes.type = codedTyp;

                    int rowNo = 1;

                    // Iterate through all rows of a particular column
                    while (true)
                    {
                        string codedVal = dt.Rows[rowNo][colNo].ToString().Trim();

                        if (codedVal.Length != 0)
                        {
                            codedTypes.values.Add(codedVal);
                        }
                        else
                        {
                            break;
                        }

                        rowNo++;

                        if(rowNo == numOfRows)
                        {
                            break;
                        }
                    }

                    // Append to the CodedTypes list
                    m_CodedTypes.Add(codedTypes);
                }
                else
                {
                    MessageBox.Show("In \"Coded-Types\" sheet, value of coded type in column " + (colNo + 1).ToString() + " should not be blank",
                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);

                    return false;
                }
            }

            return true;
        }

        bool ValidateParameterName(string parameterName, int rowNoInConfigFile)
        {
            if (parameterName.Length > 59)
            {
                MessageBox.Show("In \"Parameters\" sheet, Parameter name \"" + parameterName + "\" in row " + rowNoInConfigFile.ToString() + " and column 2 exceeds permitted lenght of 59.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                return false;
            }

            if (parameterName.Contains(' '))  // Parameter name should not have space inbetween
            {
                MessageBox.Show("In \"Parameters\" sheet, Parameter name \"" + parameterName + "\" in row " + rowNoInConfigFile.ToString() + " and column 2 contains space inbetween.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                return false;
            }

            if (!Char.IsLetter(parameterName[0]) && (parameterName[0] != '_'))  // Parameter name should start with a letter or '_'
            {
                MessageBox.Show("In \"Parameters\" sheet, Parameter name \"" + parameterName + "\" in row " + rowNoInConfigFile.ToString() + " and column 2 does not start with a letter or underscore.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                return false;
            }

            for (int i = 0; i < parameterName.Length; i++)
            {
                if (!Char.IsLetterOrDigit(parameterName[i]) && (parameterName[i] != '_'))
                {
                    MessageBox.Show("In \"Parameters\" sheet, Parameter name \"" + parameterName + "\" in row " + rowNoInConfigFile.ToString() + " and column 2 contains one or more characters that are not alphanumeric nor underscores.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }
            }

            return true;
        }


        /**
         * @brief This function reads the "1553-Parameters" sheet of excel config file and adds EguParameter
         *          objects to the corresponding messages. This function must be called after calling
         *          Read1553MessageListFromExcel().
         * @return true if successful, false otherwise.
         */
        public bool Read1553ParameterListFromExcel(ref ushort[] numRows, List<CodedType> m_CodedTypes)
        {
            int currentWordIndex, previousWordIndex = -1;
            byte numOfParams = 0;
            string currentMsgName, prevMsgName = "";

            /* Read list of EGU parameters */

            int numOfRows = dsresult.Tables[EXCEL_SHEET_1553PARAMETERS].Rows.Count;
            DataTable dt = dsresult.Tables[EXCEL_SHEET_1553PARAMETERS];

            for (byte ctr = 0; ctr < NUM_1553_CHANNELS; ctr++)
            {
                Msg1553 pMsg = null;

                ushort displayRowNo = 0;

                for (int rowNo = 1; rowNo < numOfRows; rowNo++)
                {
                    string msgName = dt.Rows[rowNo][0].ToString().Trim();

                    if (msgName.StartsWith("//"))  // Ignore if the line is commented
                    {
                        continue;
                    }

                    if (msgName == "")
                    {
                        /* Empty msg name indicates this is a new parameter entry into the last found message name */

                        if (pMsg == null)
                        {
                            // TODO: Show error message, the first line is likely without a message name which is not allowed
                            //qDebug() << "Blank message name encountered in ReadParameterListFromExcel()";
                            continue;
                        }
                    }
                    else
                    {
                        pMsg = new Msg1553();   //doubt

                        // List of messages was already read and stored in the msgList member variable. Using the message name
                        // as the index, locate corresponding Msg1553 object
                        bool retValBool = pFrame[ctr].FindMessageInList(msgName, ref pMsg);
                        if (!retValBool)
                        {
                            // TODO: Message not found in messages sheet. Integrity error
                            /*                            MessageBox.Show("In \"Parameters\" sheet, message name \"" + msgName + "\" in row " + (rowNo + 1).ToString() + " not found in messages sheet.",
                                                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                                                        return false;*/
                            continue;
                        }
                        else
                        {
                            pMsg.setTimeTagResolution(ddc1553Constants.TTResValues.ACE_TT_4US);
                        }
                    }

                    /* If we reach here it means we have a valid pointer to the message to which this parameter belongs. Let's proceed
                        with reading rest of the parameter info, allocating space to this parameter and populating it */
                    if (dt.Rows[rowNo][1].ToString().Trim().Length != 0)
                    {
                        EguParameter param = new EguParameter();
                        param.name = dt.Rows[rowNo][1].ToString();
                        // remove leading and trailing whitespaces
                        param.name = param.name.Trim();

                        if (!ValidateParameterName(param.name, rowNo + 1))   // check if parameter name is valid
                        {
                            return false;
                        }

                        // data type
                        param.dataType = dt.Rows[rowNo][2].ToString().Trim();
                        if ((param.dataType.ToUpper() != "UNSIGNED") &&
                            (param.dataType.ToUpper() != "INTEGER") &&
                            (param.dataType.ToUpper() != "REALIEEE754") &&
                            (param.dataType.ToUpper() != "CODED"))
                        {
                            MessageBox.Show("In \"Parameters\" sheet, DATATYPE in row " + (rowNo + 1).ToString() + " and column 3 is invalid. Valid values are:\nUNSIGNED\nINTEGER\nREALIEEE754\nCODED",
                                                "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }

                        // Length
                        try
                        {
                            param.length = UInt32.Parse(dt.Rows[rowNo][3].ToString());

                            if (!(param.length >= 1 && param.length <= 64))
                            {
                                MessageBox.Show("In \"Parameters\" sheet, parameter length in row " + (rowNo + 1).ToString() + " and column 4 is not between 1 and 64.",
                                                "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                                return false;
                            }
                        }
                        catch (Exception)
                        {
                            MessageBox.Show("In \"Parameters\" sheet, parameter length in row " + (rowNo + 1).ToString() + " and column 4 is invalid.",
                                                "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }

                        // Start word
                        try
                        {
                            param.startWord = UInt32.Parse(dt.Rows[rowNo][4].ToString());

                            if (!(param.startWord >= 1 && param.startWord <= 32))
                            {
                                MessageBox.Show("In \"Parameters\" sheet, starting word in row " + (rowNo + 1).ToString() + " and column 5 is not between 1 and 32.",
                                                "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                                return false;
                            }

                            param.startWord -= 1;    // for further processing
                        }
                        catch (Exception)
                        {
                            MessageBox.Show("In \"Parameters\" sheet, starting word in row " + (rowNo + 1).ToString() + " and column 5 is invalid.",
                                                "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }

                        // start bit
                        try
                        {
                            param.startBit = UInt32.Parse(dt.Rows[rowNo][5].ToString());

                            if (!(param.startBit >= 1 && param.startBit <= 16))
                            {
                                MessageBox.Show("In \"Parameters\" sheet, starting bit in row " + (rowNo + 1).ToString() + " and column 6 is not between 1 and 16.",
                                                "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                                return false;
                            }

                            param.startBit -= 1;    // for further processing
                        }
                        catch (Exception)
                        {
                            MessageBox.Show("In \"Parameters\" sheet, starting bit in row " + (rowNo + 1).ToString() + " and column 6 is invalid.",
                                                "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }

                        // Verify that start bit + length does not go over word length (16 bits)
                        /*                    if (!((param.startBit + param.length) >= 1 && (param.startBit + param.length) <= 16))
                                            {
                                                QMessageBox::critical(this,
                                                                      "Config file error",
                                                                      "In \"Parameters\" sheet, Error in row " + QString::number(rowNo) + ", starting bit+length should be between 1 and 16",
                                                                      QMessageBox::Ok);
                                                return false;
                                            }*/

                        // Scaling factor
                        try
                        {
                            param.scaleFactor = Double.Parse(dt.Rows[rowNo][6].ToString());
                        }
                        catch (Exception)
                        {
                            MessageBox.Show("In \"Parameters\" sheet, Scaling factor in row " + (rowNo + 1).ToString() + " and column 7 is invalid.",
                                                "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }

                        // offset
                        try
                        {
                            param.offset = Double.Parse(dt.Rows[rowNo][7].ToString());

                            if (!(param.offset >= 0 && param.offset <= 15))
                            {
                                MessageBox.Show("In \"Parameters\" sheet, offset in row " + (rowNo + 1).ToString() + " and column 8 is not between 0 and 15.",
                                                "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                                return false;
                            }
                        }
                        catch (Exception)
                        {
                            MessageBox.Show("In \"Parameters\" sheet, offset in row " + (rowNo + 1).ToString() + " and column 8 is invalid.",
                                                "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }

                        param.units = dt.Rows[rowNo][8].ToString().Trim();

                        param.codedType = dt.Rows[rowNo][9].ToString().Trim();
                        if (param.codedType.Length != 0)
                        {
                            if (param.dataType.ToUpper() == "CODED")
                            {
                                bool matchFound = false;
                                foreach (CodedType ct in m_CodedTypes)
                                {
                                    if (ct.type == param.codedType)
                                    {
                                        matchFound = true;
                                        break;
                                    }
                                }
                                if (matchFound == false)
                                {
                                    MessageBox.Show("In \"Parameters\" sheet, CODED_TYPE in row " + (rowNo + 1).ToString() + " and column 10 should match one of the types given in \"Coded-Types\" sheet.",
                                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);

                                    return false;
                                }
                            }
                            else
                            {
                                MessageBox.Show("In \"Parameters\" sheet, CODED_TYPE in row " + (rowNo + 1).ToString() + " and column 10 should be blank for this data type.",
                                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);

                                return false;
                            }
                        }

                        // is REVERSE_BITS
                        param.isReverseBits = dt.Rows[rowNo][10].ToString().Trim();
                        if ((param.isReverseBits.ToUpper() != "YES") &&
                            (param.isReverseBits.ToUpper() != ""))
                        {
                            MessageBox.Show("In \"Parameters\" sheet, REVERSE_BITS in row " + (rowNo + 1).ToString() + " and column 11 is invalid. Valid values are:\nYES\nBlank Value",
                                                "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }

                        // Set default value
                        //QString defaultValueStr = paramSheet->read(rowNo, 13).toString().trimmed();
                        string defaultValueStr = dt.Rows[rowNo][11].ToString().Trim();
                        string errorStr = "";
                        //if (!param.SetDefaultValue("", ref errorStr, m_CodedTypes))
                        if (!param.SetDefaultValue(defaultValueStr, ref errorStr, m_CodedTypes))
                        {
                            MessageBox.Show("In \"Parameters\" sheet, in row " + (rowNo + 1).ToString() + " and column 12. " + errorStr,
                                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);

                            return false;
                        }

                        param.pMsg = pMsg;

                        currentMsgName = param.pMsg.name;
                        if (currentMsgName != prevMsgName)
                        {
                            prevMsgName = currentMsgName;
                            previousWordIndex = -1;
                            numOfParams = 0;
                        }

                        currentWordIndex = (int)param.startWord;
                        if (currentWordIndex == previousWordIndex)
                        {
                            numOfParams++;
                        }
                        else
                        {
                            previousWordIndex = currentWordIndex;
                            numOfParams = 1;
                        }

                        param.pMsg.wordInfo[param.startWord].numOfParameters = numOfParams;

                        // Duplicate check
                        foreach (EguParameter p in pMsg.eguParams)
                        {
                            if (p.name == param.name)
                            {
                                MessageBox.Show("In \"Parameters\" sheet, Parameter name \"" + param.name + "\" in row " + (rowNo + 1).ToString() + " and column 2 is duplicated.",
                                                "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                                return false;
                            }
                        }

                        param.displayRowNo = displayRowNo;

                        displayRowNo++;

                        // All well. Add parameter to message
                        pMsg.AddNewEguParameter(param);
                    }

                }

                numRows[ctr] = displayRowNo;
            }

            return true;
        }

        /**
         * @brief This function reads the "Frames" worksheet of ETSM config file and populates
         *          "frameList" from this information. This function must be called after calling
         *          ReadMessageListFromExcel().
         * @return true if successful, false otherwise.
         */
        public bool ReadFrameListFromExcel(/*ref MajorFrame majFrame*/byte devNum)
        {
            /* Read all frames from the "Frames" sheet */

            ushort sheetNo = 0;
            if(devNum == 0)
            {
                sheetNo = EXCEL_SHEET_1553FRAMES_CHAN1;
            }
            else if (devNum == 1)
            {
                sheetNo = EXCEL_SHEET_1553FRAMES_CHAN2;
            }
            int numOfRows = dsresult.Tables[sheetNo].Rows.Count;
            DataTable dt = dsresult.Tables[sheetNo];

            MinorFrame pfrmStruct = null;
            string tempStr;

            for (int rowNo = 1; rowNo < numOfRows; rowNo++)
            {
                Msg1553 pMsg = new Msg1553();

                tempStr = dt.Rows[rowNo][0].ToString().Trim();

                if (tempStr.StartsWith("//"))  // Ignore if the line is commented
                {
                    continue;
                }

                if (tempStr != "")
                {
                    /* This line is beginning of a new frame entry because the frame name column is not empty. So, append the previous
                     * frame into the list (unless this itself is the first frame entry and begin with a new one from here */
                    if (pfrmStruct != null)
                    {
                        pFrame[devNum].minorFrames.Add(pfrmStruct);
                    }

                    /* Create space for the new frame and populate it */
                    pfrmStruct = new MinorFrame();
                    pfrmStruct.name = tempStr;
                    //try
                    //{
                    //    pfrmStruct.period = UInt32.Parse(dt.Rows[rowNo][1].ToString());

                    //    /*if (!(pfrmStruct.period >= 0 && pfrmStruct.period <= 15))
                    //    {
                    //        MessageBox.Show("In \"Frames\" sheet, minor frame period in row " + (rowNo + 1).ToString() + " and column 1 is not between 0 and 15.",
                    //                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    //        return false;
                    //    }*/
                    //}
                    //catch (Exception)
                    //{
                    //    MessageBox.Show("In \"Frames\" sheet, minor frame period in row " + (rowNo + 1).ToString() + " and column 1 is invalid.",
                    //                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    //    return false;
                    //}
                }

                /* Next read the message name, locate its message structure within the message list and add a pointer to it to the list */
                tempStr = dt.Rows[rowNo][1].ToString().Trim();
                bool retValBool = pFrame[devNum].FindMessageInList(tempStr, ref pMsg);
                if (retValBool)
                {
                    pfrmStruct.msgs.Add(pMsg);
                }
                else
                {
                    if (tempStr.Length != 0)
                    {
                        MessageBox.Show("In \"Frames\" sheet, message name \"" + tempStr + "\" in row " + (rowNo + 1).ToString() + " not found in messages sheet.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        //delete pfrmStruct;
                        return false;
                    }
                }

            }

            /* Add the last frame */
            pFrame[devNum].minorFrames.Add(pfrmStruct);

            return true;
        }

        /**
        * @brief This function reads the "429-Labels" worksheet of excel config file and populates
        *          the msgList member variable.
        * @return true if successful, false otherwise.
        */
        public bool ReadArincMessageListFromExcel()
        {
            int rowNo;
            List<string> labelNames = new List<string>();

            /* Read all messages from the "429-Labels" sheet */

            int numOfRows = dsresult.Tables[EXCEL_SHEET_ARINCMESSAGES].Rows.Count;
            DataTable dt = dsresult.Tables[EXCEL_SHEET_ARINCMESSAGES];

            for (rowNo = 1; rowNo < numOfRows; rowNo++)
            {
                MsgArinc429 newMsg = new MsgArinc429();

                newMsg.labelName = dt.Rows[rowNo][0].ToString().Trim();

                // remove leading and trailing whitespaces
                newMsg.labelName = newMsg.labelName.Trim();

                if (newMsg.labelName.Length == 0)  // Ignore if the line is junk
                {
                    continue;
                }

                if (newMsg.labelName.StartsWith("//"))  // Ignore if the line is commented
                {
                    continue;
                }

                if (newMsg.labelName.Contains(' '))  // Message name should not have space inbetween
                {
                    MessageBox.Show("In \"429-Labels\" sheet, label name \"" + newMsg.labelName + "\" in row " + (rowNo + 1).ToString() + " and column 1 contains space inbetween.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }

                labelNames.Add(newMsg.labelName);
                // Check for duplicate message name
                for (int ctr = 0; ctr < labelNames.Count - 1; ctr++)
                {
                    if (newMsg.labelName == labelNames[ctr])
                    {
                        MessageBox.Show("In \"429-Labels\" sheet, label name \"" + newMsg.labelName + "\" in row " + (rowNo + 1).ToString() + " and column 1 is duplicate.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }
                }

                try
                {
                    int parsedInt = Convert.ToInt32(dt.Rows[rowNo][1].ToString().Trim(), 8); // Parses string as octal
                    newMsg.labelValue = (byte)parsedInt; // Casts the integer value to a byte
                }
                catch (Exception)
                {
                    MessageBox.Show("In \"429-Labels\" sheet, label value in row " + (rowNo + 1).ToString() + " and column 2 is invalid.",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }

                newMsg.type = dt.Rows[rowNo][2].ToString().Trim();
                if ((newMsg.type != "RX") &&
                    (newMsg.type != "TX"))
                {
                    MessageBox.Show("In \"429-Labels\" sheet, TYPE in row " + (rowNo + 1).ToString() + " and column 3 is invalid. Valid values are:\nTX\nRX",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }

                newMsg.channel = dt.Rows[rowNo][4].ToString().Trim();
                if ((newMsg.channel != "1") &&
                    (newMsg.channel != "2") &&
                    (newMsg.channel != "Both"))
                {
                    MessageBox.Show("In \"429-Labels\" sheet, channel in row " + (rowNo + 1).ToString() + " and column 5 is invalid. Valid values are:\n1\n2\nBoth",
                                        "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    return false;
                }

                pArincMsgs.Add(newMsg);
            }

            return true;
        }

        /**
         * @brief This function reads the "429-Parameters" sheet of excel config file and adds EguParameter
         *          objects to the corresponding messages. This function must be called after calling
         *          ReadArincMessageListFromExcel().
         * @return true if successful, false otherwise.
         */
        public bool ReadArincParameterListFromExcel(ref ushort numRowsChan1, ref ushort numRowsChan2, List<CodedType> m_CodedTypes)
        {
            /* Read list of EGU parameters */

            int numOfRows = dsresult.Tables[EXCEL_SHEET_ARINCPARAMETERS].Rows.Count;
            DataTable dt = dsresult.Tables[EXCEL_SHEET_ARINCPARAMETERS];

            MsgArinc429 pMsg = null;

            ushort displayRowNoChan1 = 0, displayRowNoChan2 = 0;

            for (int rowNo = 1; rowNo < numOfRows; rowNo++)
            {
                string labelName = dt.Rows[rowNo][0].ToString().Trim();

                if (labelName.StartsWith("//"))  // Ignore if the line is commented
                {
                    continue;
                }

                if (labelName == "")
                {
                    /* Empty label name indicates this is a new parameter entry into the last found label name */

                    if (pMsg == null)
                    {
                        // TODO: Show error message, the first line is likely without a message name which is not allowed
                        //qDebug() << "Blank message name encountered in ReadParameterListFromExcel()";
                        continue;
                    }
                }
                else
                {
                    pMsg = new MsgArinc429();

                    // List of messages was already read and stored in the msgList member variable. Using the label name
                    // as the index, locate corresponding MsgArinc429 object
                    bool retValBool = FindArincMessageInList(labelName, ref pMsg);
                    if (!retValBool)
                    {
                        // TODO: Message not found in messages sheet. Integrity error
                        MessageBox.Show("In \"429-Parameters\" sheet, label name \"" + labelName + "\" in row " + (rowNo + 1).ToString() + " not found in 429-Labels sheet.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }
                }

                /* If we reach here it means we have a valid pointer to the message to which this parameter belongs. Let's proceed
                    with reading rest of the parameter info, allocating space to this parameter and populating it */
                if (dt.Rows[rowNo][1].ToString().Trim().Length != 0)
                {
                    EguParameterArinc429 param = new EguParameterArinc429();
                    param.name = dt.Rows[rowNo][1].ToString();
                    // remove leading and trailing whitespaces
                    param.name = param.name.Trim();

                    if (!ValidateParameterName(param.name, rowNo + 1))   // check if parameter name is valid
                    {
                        return false;
                    }

                    // data type
                    param.dataType = dt.Rows[rowNo][2].ToString().Trim();
                    if ((param.dataType.ToUpper() != "UNSIGNED") &&
                        (param.dataType.ToUpper() != "INTEGER") &&
                        (param.dataType.ToUpper() != "REALIEEE754") &&
                        (param.dataType.ToUpper() != "CODED") &&
                        (param.dataType.ToUpper() != "BCD"))
                    {
                        MessageBox.Show("In \"429-Parameters\" sheet, DATATYPE in row " + (rowNo + 1).ToString() + " and column 3 is invalid. Valid values are:\nUNSIGNED\nINTEGER\nREALIEEE754\nCODED\nBCD",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }

                    // Length
                    try
                    {
                        param.length = UInt32.Parse(dt.Rows[rowNo][3].ToString());

                        if (!(param.length >= 1 && param.length <= 19))
                        {
                            MessageBox.Show("In \"429-Parameters\" sheet, parameter length in row " + (rowNo + 1).ToString() + " and column 4 is not between 1 and 19.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }
                    }
                    catch (Exception)
                    {
                        MessageBox.Show("In \"429-Parameters\" sheet, parameter length in row " + (rowNo + 1).ToString() + " and column 4 is invalid.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }

                    // start bit
                    try
                    {
                        param.startBit = UInt32.Parse(dt.Rows[rowNo][4].ToString());

                        if (!(param.startBit >= 11 && param.startBit <= 28))
                        {
                            MessageBox.Show("In \"429-Parameters\" sheet, starting bit in row " + (rowNo + 1).ToString() + " and column 5 is not between 11 and 28.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }

                        param.startBit -= 1;    // for further processing
                    }
                    catch (Exception)
                    {
                        MessageBox.Show("In \"429-Parameters\" sheet, starting bit in row " + (rowNo + 1).ToString() + " and column 5 is invalid.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }

                    // Scaling factor
                    try
                    {
                        param.scaleFactor = Double.Parse(dt.Rows[rowNo][5].ToString());
                    }
                    catch (Exception)
                    {
                        MessageBox.Show("In \"429-Parameters\" sheet, Scaling factor in row " + (rowNo + 1).ToString() + " and column 6 is invalid.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }

                    // offset
                    try
                    {
                        param.offset = Double.Parse(dt.Rows[rowNo][6].ToString());

/*                        if (!(param.offset >= 0 && param.offset <= 15))
                        {
                            MessageBox.Show("In \"Parameters\" sheet, offset in row " + (rowNo + 1).ToString() + " and column 8 is not between 0 and 15.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }*/
                    }
                    catch (Exception)
                    {
                        MessageBox.Show("In \"429-Parameters\" sheet, offset in row " + (rowNo + 1).ToString() + " and column 7 is invalid.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return false;
                    }

                    param.units = dt.Rows[rowNo][7].ToString().Trim();

                    param.codedType = dt.Rows[rowNo][8].ToString().Trim();
                    if (param.codedType.Length != 0)
                    {
                        if (param.dataType.ToUpper() == "CODED")
                        {
                            bool matchFound = false;
                            foreach (CodedType ct in m_CodedTypes)
                            {
                                if (ct.type == param.codedType)
                                {
                                    matchFound = true;
                                    break;
                                }
                            }
                            if (matchFound == false)
                            {
                                MessageBox.Show("In \"429-Parameters\" sheet, CODED_TYPE in row " + (rowNo + 1).ToString() + " and column 9 should match one of the types given in \"Coded-Types\" sheet.",
                                                    "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);

                                return false;
                            }
                        }
                        else
                        {
                            MessageBox.Show("In \"429-Parameters\" sheet, CODED_TYPE in row " + (rowNo + 1).ToString() + " and column 9 should be blank for this data type.",
                                                    "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);

                            return false;
                        }
                    }

                    // Set default value
                    //QString defaultValueStr = paramSheet->read(rowNo, 13).toString().trimmed();
                    string errorStr = "";
                    if (!param.SetDefaultValue("", ref errorStr, m_CodedTypes))
                    {
                        MessageBox.Show("In \"429-Parameters\" sheet, in row " + (rowNo + 1).ToString() + " and column 11. " + errorStr,
                                                    "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);

                        return false;
                    }

                    param.pMsg = pMsg;

                    // Duplicate check
                    foreach (EguParameterArinc429 p in pMsg.eguParams)
                    {
                        if (p.name == param.name)
                        {
                            MessageBox.Show("In \"429-Parameters\" sheet, Parameter name \"" + param.name + "\" in row " + (rowNo + 1).ToString() + " and column 2 is duplicated.",
                                            "Config file error", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            return false;
                        }
                    }

                    if(pMsg.channel == "1" || pMsg.channel == "Both")
                    {
                        param.displayRowNoChan1 = displayRowNoChan1;
                        displayRowNoChan1++;
                    }

                    if (pMsg.channel == "2" || pMsg.channel == "Both")
                    {
                        param.displayRowNoChan2 = displayRowNoChan2;
                        displayRowNoChan2++;
                    }

                    // All well. Add parameter to message
                    pMsg.AddNewEguParameter(param);
                }

            }

            numRowsChan1 = displayRowNoChan1;
            numRowsChan2 = displayRowNoChan2;

            return true;
        }

        /**
         * @brief This function searches for and returns a pointer to the message object in the message
         *          list whose name matches that passed as argument to this function.
         * @param labelName The name of the message to match
         * @return A pointer to the matched message object
         */
        public bool FindArincMessageInList(string labelName, ref MsgArinc429 pMsg)
        {
            /* Travers through the message list and look for a message with the name as in
             * msgName argument */
            foreach (MsgArinc429 msg in pArincMsgs)
            {
                if (msg.labelName == labelName)
                {
                    /* Found it! Stop search and return this message pointer */
                    pMsg = msg;
                    return true;
                }
            }

            pMsg = null;
            return false;
        }

    }
}
