public async Task InitiateSimulationAsync()
        {
            string logPrefix = "system".BuildLogPrefix();

            try
            {
                //Connectivity tests
                //Control if a connection string exists (ideally, stored in TPM/HSM or any secured location.
                //If there is no connection string, check if the DPS settings are provided.
                //If so, provision the device and persist the connection string for upcoming boots.
                if (string.IsNullOrEmpty(ModuleSettings.ConnectionString))
                {
                    ModuleSettings.ConnectionString = await _provisioningService.AddModuleIdentityToDevice(ModuleSettings.ModuleId);

                    if (string.IsNullOrEmpty(ModuleSettings.ConnectionString))
                    {
                        _logger.LogWarning($"{logPrefix}::{ModuleSettings.ArtifactId}::No module connection string has been created.");
                    }
                    else
                    {
                        _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::Module connection string being persisted.");
                        await ConfigurationHelpers.WriteModulesSettings(ModuleSettings, _environmentName);
                    }
                }

                IoTTools.CheckModuleConnectionStringData(ModuleSettings.ConnectionString, _logger);

                // Connect to the IoT hub using the MQTT protocol
                _moduleClient = ModuleClient.CreateFromConnectionString(ModuleSettings.ConnectionString, Microsoft.Azure.Devices.Client.TransportType.Mqtt);
                _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::Module client created.");

                if (SimulationSettings.EnableTwinPropertiesDesiredChangesNotifications)
                {
                    await _moduleClient.SetDesiredPropertyUpdateCallbackAsync(OnDesiredPropertyChange, null);

                    _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::Twin Desired Properties update callback handler registered.");
                }

                //Configuration
                if (SimulationSettings.EnableC2DDirectMethods)
                {
                    //Register C2D Direct methods handlers
                    await RegisterC2DDirectMethodsHandlersAsync(_moduleClient, ModuleSettings, _logger);
                }

                if (SimulationSettings.EnableC2DMessages)
                {
                    //Start receiving C2D messages

                    ReceiveC2DMessagesAsync(_moduleClient, ModuleSettings, _logger);
                }

                //Messages
                if (SimulationSettings.EnableTelemetryMessages)
                {
                    SendDeviceToCloudMessagesAsync(_moduleClient, ModuleSettings.DeviceId, ModuleSettings.ModuleId, _logger); //interval is a global variable changed by processes
                }
                if (SimulationSettings.EnableErrorMessages)
                {
                    SendDeviceToCloudErrorAsync(_moduleClient, ModuleSettings.DeviceId, ModuleSettings.ModuleId, SimulationSettings.ErrorFrecuency, _logger);
                }

                if (SimulationSettings.EnableCommissioningMessages)
                {
                    SendDeviceToCloudCommissioningAsync(_moduleClient, ModuleSettings.DeviceId, ModuleSettings.ModuleId, SimulationSettings.CommissioningFrecuency, _logger);
                }

                if (SimulationSettings.EnableReadingTwinProperties)
                {
                    //Twins
                    _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::INITIALIZATION::Retrieving twin.");
                    Twin twin = await _moduleClient.GetTwinAsync();

                    if (twin != null)
                    {
                        _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::INITIALIZATION::Device twin: {JsonConvert.SerializeObject(twin, Formatting.Indented)}.");
                    }
                    else
                    {
                        _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::INITIALIZATION::No device twin.");
                    }
                }

                _moduleClient.SetConnectionStatusChangesHandler(new ConnectionStatusChangesHandler(ConnectionStatusChanged));
            }
            catch (ConnectionStringException ex)
            {
                _logger.LogError($"{logPrefix}::{ModuleSettings.ArtifactId}::ConnectionStringException:{ex.Message}");
            }
            catch (Exception ex)
            {
                _logger.LogError($"{logPrefix}::{ModuleSettings.ArtifactId}::{ex.Message}");
            }
        }