def start(self):
        '''
        Turn on the master server components
        '''
        self._pre_flight()
        log.info('salt-master is starting as user \'%s\'', salt.utils.user.get_user())

        enable_sigusr1_handler()
        enable_sigusr2_handler()

        self.__set_max_open_files()

        # Reset signals to default ones before adding processes to the process
        # manager. We don't want the processes being started to inherit those
        # signal handlers
        with salt.utils.process.default_signals(signal.SIGINT, signal.SIGTERM):

            # Setup the secrets here because the PubServerChannel may need
            # them as well.
            SMaster.secrets['aes'] = {
                'secret': multiprocessing.Array(
                    ctypes.c_char,
                    salt.utils.stringutils.to_bytes(
                        salt.crypt.Crypticle.generate_key_string()
                    )
                ),
                'reload': salt.crypt.Crypticle.generate_key_string
            }
            log.info('Creating master process manager')
            # Since there are children having their own ProcessManager we should wait for kill more time.
            self.process_manager = salt.utils.process.ProcessManager(wait_for_kill=5)
            pub_channels = []
            log.info('Creating master publisher process')
            log_queue = salt.log.setup.get_multiprocessing_logging_queue()
            for _, opts in iter_transport_opts(self.opts):
                chan = salt.transport.server.PubServerChannel.factory(opts)
                chan.pre_fork(self.process_manager, kwargs={'log_queue': log_queue})
                pub_channels.append(chan)

            log.info('Creating master event publisher process')
            self.process_manager.add_process(salt.utils.event.EventPublisher, args=(self.opts,))

            if self.opts.get('reactor'):
                if isinstance(self.opts['engines'], list):
                    rine = False
                    for item in self.opts['engines']:
                        if 'reactor' in item:
                            rine = True
                            break
                    if not rine:
                        self.opts['engines'].append({'reactor': {}})
                else:
                    if 'reactor' not in self.opts['engines']:
                        log.info('Enabling the reactor engine')
                        self.opts['engines']['reactor'] = {}

            salt.engines.start_engines(self.opts, self.process_manager)

            # must be after channels
            log.info('Creating master maintenance process')
            self.process_manager.add_process(Maintenance, args=(self.opts,))

            if self.opts.get('event_return'):
                log.info('Creating master event return process')
                self.process_manager.add_process(salt.utils.event.EventReturn, args=(self.opts,))

            ext_procs = self.opts.get('ext_processes', [])
            for proc in ext_procs:
                log.info('Creating ext_processes process: %s', proc)
                try:
                    mod = '.'.join(proc.split('.')[:-1])
                    cls = proc.split('.')[-1]
                    _tmp = __import__(mod, globals(), locals(), [cls], -1)
                    cls = _tmp.__getattribute__(cls)
                    self.process_manager.add_process(cls, args=(self.opts,))
                except Exception:
                    log.error('Error creating ext_processes process: %s', proc)

            if HAS_HALITE and 'halite' in self.opts:
                log.info('Creating master halite process')
                self.process_manager.add_process(Halite, args=(self.opts['halite'],))

            # TODO: remove, or at least push into the transport stuff (pre-fork probably makes sense there)
            if self.opts['con_cache']:
                log.info('Creating master concache process')
                self.process_manager.add_process(salt.utils.master.ConnectedCache, args=(self.opts,))
                # workaround for issue #16315, race condition
                log.debug('Sleeping for two seconds to let concache rest')
                time.sleep(2)

            log.info('Creating master request server process')
            kwargs = {}
            if salt.utils.platform.is_windows():
                kwargs['log_queue'] = log_queue
                kwargs['log_queue_level'] = salt.log.setup.get_multiprocessing_logging_level()
                kwargs['secrets'] = SMaster.secrets

            self.process_manager.add_process(
                ReqServer,
                args=(self.opts, self.key, self.master_key),
                kwargs=kwargs,
                name='ReqServer')

            self.process_manager.add_process(
                FileserverUpdate,
                args=(self.opts,))

            # Fire up SSDP discovery publisher
            if self.opts['discovery']:
                if salt.utils.ssdp.SSDPDiscoveryServer.is_available():
                    self.process_manager.add_process(salt.utils.ssdp.SSDPDiscoveryServer(
                        port=self.opts['discovery']['port'],
                        listen_ip=self.opts['interface'],
                        answer={'mapping': self.opts['discovery'].get('mapping', {})}).run)
                else:
                    log.error('Unable to load SSDP: asynchronous IO is not available.')
                    if sys.version_info.major == 2:
                        log.error('You are using Python 2, please install "trollius" module to enable SSDP discovery.')

        # Install the SIGINT/SIGTERM handlers if not done so far
        if signal.getsignal(signal.SIGINT) is signal.SIG_DFL:
            # No custom signal handling was added, install our own
            signal.signal(signal.SIGINT, self._handle_signals)

        if signal.getsignal(signal.SIGTERM) is signal.SIG_DFL:
            # No custom signal handling was added, install our own
            signal.signal(signal.SIGTERM, self._handle_signals)

        self.process_manager.run()