public static Dictionary <string, IMonoChannel> GetChannelsFromXml(string filename)
        {
            var channels = new Dictionary <string, IMonoChannel>();

            //TODO: make static factory for each iface type
            Log.Log("Loading BUMIZ IO Manager from XML file " + filename + "...");
            var docChannels = XDocument.Load(filename);

            {
                var rootNode = docChannels.Element("BumizChannels");
                if (rootNode != null)
                {
                    var comChannels = rootNode.Elements("ComPortChannel");
                    foreach (var comChannel in comChannels)
                    {
                        try {
                            var channelLabel           = comChannel.Attribute("Label").Value;
                            var comName                = comChannel.Attribute("PortName").Value;
                            var baudRate               = int.Parse(comChannel.Attribute("BaudRate").Value);
                            var onlineCheckTimeSeconds = int.Parse(comChannel.Attribute("OnlineCheckTimeSeconds").Value);
                            var checkNetAddress        = bool.Parse(comChannel.Attribute("CheckNetAddress").Value);

                            Log.Log("Loaded COM channel config from XML with name  " + channelLabel + ", COM port name is " +
                                    comName + ", it's baud rate is " + baudRate);

                            var subChannel = new SerialChannelSimple(comName, baudRate, 15);
                            Log.Log("SerialChannelSimple was created using XML config [OK]");

                            var channel = new BumizAdvancedNetwork(subChannel, null, onlineCheckTimeSeconds, checkNetAddress);
                            Log.Log("BumizAdvancedNetwork was created base on SerialChannelSimple [OK]");

                            channels.Add(channelLabel, channel);
                        }
                        catch (Exception ex) {
                            Log.Log("Error during loading information fomr XML config for single COM channel: " + ex);
                        }
                    }
                }
            }
            Log.Log("Creating BUMIZ IO channels from config is complete, final channels count is: " + channels.Count);
            return(channels);
        }
        public BumizAdvancedNetwork(SerialChannelSimple channelSimple, Action queueChangedCallback,
                                    int onlineCheckTimeSeconds, bool checkInteleconAddress)
        {
            Log.Log("Создание канала сети БУМИЗ поверх COM-порта...");

            _addressMap         = new DNetIdsFileDataStorage("DNetIdStorage");
            _linkQualityStorage = new LinkQualityStorage();

            _channelSimple   = channelSimple ?? throw new Exception("SerialChannelSimple cannot be null");
            _onlineCheckTime = TimeSpan.FromSeconds(onlineCheckTimeSeconds);

            QueueChangedCallback   = queueChangedCallback;
            _checkInteleconAddress = checkInteleconAddress;
            _queueLength           = 0;


            _queueWorker = new SingleThreadedRelayMultiQueueWorker <Action>("BumizAdvancedNetwork.QueueWorker", a => a(),
                                                                            ThreadPriority.Normal, true, null, null, 5); // 5 levels of IO priority
            _notifyWorker =
                new SingleThreadedRelayQueueWorkerProceedAllItemsBeforeStopNoLog <Action>("BumizAdvancedNetwork.NotifyWorker",
                                                                                          a => a(), ThreadPriority.Normal, true, null);

            Log.Log("Создание сети завершено");
        }