internal ExecutionContext(Configuration configuration, BlockingCollection<BookDescriptor> books, ConcurrentDictionary<BookDescriptor, BookDescriptor> removedBooks)
        {
            Contract.Requires(configuration != null);
            Contract.Requires(books != null);
            Contract.Requires(removedBooks != null);

            _configuration = configuration;
            _books = books;
            _removedBooks = removedBooks;
            _receiver = _configuration.AutostartConversion ? (IBookReceiver)new ImmediateReceiver(_books) : new TriggeredReceiver(_books);

            _task = Task.Factory.StartNew(TaskWorker, this);
        }
        public MainForm(Engine engine, Configuration configuration)
        {
            Contract.Requires(engine != null);
            Contract.Requires(configuration != null);

            _logger.EnterFunction();

            _engine = engine;
            _configuration = configuration;

            _books = new ConcurrentDictionary<BookDescriptor, ListViewItem>();

            _dndHandlers = new DropHandlers();
            _dndHandlers.Add(new FileDropHandler());

            _appLogForm = new ApplicationLogForm();
            LogTabPage appLogPage = _appLogForm.AddLogPage("Application");
            AppLogAppender appLogAppender = LogManager.Instance.Appenders[AppLogAppender.ID] as AppLogAppender;
            if (appLogAppender != null) {
                appLogAppender.SetConsumer(appLogPage);
            }

            _bookLogAppenders = new List<BookLogAppender>();
            foreach (ExecutionContext context in _engine.Contexts) {
                LogTabPage page = _appLogForm.AddLogPage("Worker");
                _bookLogAppenders.Add(new BookLogAppender(page, context));

                context.BookChanged += OnBookChanged;
            }

            _engine.BookAdded += OnBookAdded;
            _engine.BookRemoved += OnBookRemoved;

            InitializeComponent();
            InitializeComponents();

            _toolStripButtonConvert.Enabled = !_configuration.AutostartConversion;

            _logger.LeaveFunction();
        }
        private static void StartApplication()
        {
            LogManager logman = LogManager.Instance;
            logman.LoadConfiguration(Path.Combine(FolderProvider.Profile, Constants.LoggerFile));
            FileAppender appender = (FileAppender)logman.Appenders[FileAppender.ID];
            if (appender != null) {
                string filename = Path.GetFileName(appender.Filename);
                appender.Filename = Path.Combine(FolderProvider.Profile, filename);
            }
            logman.Appenders.Add(new AppLogAppender());

            Configuration configuration = new Configuration();
            configuration.Load();

            using (Engine engine = new Engine(configuration)) {
                Application.EnableVisualStyles();
                Application.SetCompatibleTextRenderingDefault(false);
                Application.Run(new MainForm(engine, configuration));
            }

            logman.Close();
        }
        internal Engine(Configuration configuration)
        {
            Contract.Requires(configuration != null);

            _logger.EnterFunction();

            _configuration = configuration;

            _books = new BlockingCollection<BookDescriptor>();
            _removedBooks = new ConcurrentDictionary<BookDescriptor, BookDescriptor>();

            _inputFormats = new InputFormats();
            _outputFormats = new OutputFormats();

            List<ExecutionContext> contexts = new List<ExecutionContext>();
            for (int i = 0; i < Environment.ProcessorCount; i++) {
                contexts.Add(new ExecutionContext(_configuration, _books, _removedBooks));
            }
            _contexts = contexts.AsReadOnly();

            ValidateConverterPath();

            _logger.LeaveFunction();
        }