private static IEnumerable <ErrorInfoAdapter> GetErrorsFromUnparsed(string plogFilename, out string solutionName)
        {
            var plogTable          = new DataTable();
            var solutionPathsTable = new DataTable();

            DataTableUtils.CreatePVSDataTable(plogTable, solutionPathsTable, plogTable.DefaultView);
            var plogSet = new DataSet();

            plogSet.Tables.Add(solutionPathsTable);
            plogSet.Tables.Add(plogTable);

            var signaller = new ManualResetEventSlim(false);

            try
            {
                var       tasksQueue          = new ConcurrentQueue <Task <IEnumerable <ErrorInfo> > >();
                Exception processingException = null;
                var       processingThread    = new Thread(() =>
                {
                    try
                    {
                        while (true)
                        {
                            Task <IEnumerable <ErrorInfo> > currentTask;
                            while (tasksQueue.TryDequeue(out currentTask))
                            {
                                foreach (var error in currentTask.Result)
                                {
                                    DataTableUtils.AppendErrorInfoToDataTable(plogTable, error);
                                }
                            }

                            if (signaller.IsSet && tasksQueue.Count == 0)
                            {
                                return;
                            }

                            Thread.Sleep(1000);
                        }
                    }
                    catch (Exception e)
                    {
                        Volatile.Write <Exception>(ref processingException, e);
                    }
                });

                processingThread.Start();

                const int      linesToRead     = 10000;
                const int      maxTasksCount   = 1000000 / linesToRead;                //will consume approximately 1GB of memory
                StringBuilder  totalLinesCache = new StringBuilder(linesToRead * 350); //we assume that an average PVS-Studio output line is 350 chars long
                IList <String> preprocessedFilesDependencies;
                Func <bool>    isProcessingExceptionPresent = () => Volatile.Read <Exception>(ref processingException) != null;

                using (StreamReader logfileStream = new StreamReader(plogFilename))
                {
                    String currentLine;
                    int    linesRead = 0;
                    bool   isEncoded = false;

                    while (true)
                    {
                        if (isProcessingExceptionPresent())
                        {
                            break;
                        }

                        currentLine = logfileStream.ReadLine();
                        if (currentLine == null || linesRead >= linesToRead)
                        {
                            linesRead = 0;
                            var linesText = totalLinesCache.ToString();
                            totalLinesCache.Clear();

                            Encoding currentIncodingLocal = logfileStream.CurrentEncoding;
                            bool     isIncodedLocal       = isEncoded;

                            var errorsTask = new Task <IEnumerable <ErrorInfo> >(() => ErrorInfo.ProcessAnalyzerOutput(String.Empty,
                                                                                                                       String.Empty,
                                                                                                                       String.Empty,
                                                                                                                       linesText,
                                                                                                                       isIncodedLocal,
                                                                                                                       currentIncodingLocal,
                                                                                                                       null,
                                                                                                                       out preprocessedFilesDependencies,
                                                                                                                       String.Empty));
                            errorsTask.Start();
                            tasksQueue.Enqueue(errorsTask);

                            while (!isProcessingExceptionPresent() && tasksQueue.Count >= maxTasksCount)
                            {
                                Thread.Sleep(1000);
                            }

                            if (currentLine == null)
                            {
                                signaller.Set();
                                break;
                            }
                        }

                        if (String.IsNullOrWhiteSpace(currentLine) || currentLine.StartsWith("#"))
                        {
                            continue;
                        }

                        if (currentLine.StartsWith(CppAnalyzerDecoder.EncodeMarker))
                        {
                            isEncoded = true;
                            continue;
                        }

                        totalLinesCache.Append(currentLine + Environment.NewLine);
                        linesRead++;
                    }
                }

                processingThread.Join();

                if (isProcessingExceptionPresent())
                {
                    throw Volatile.Read <Exception>(ref processingException);
                }
            }
            finally
            {
                signaller.Set();
            }

            return(GetErrorsFromXml(out solutionName, plogSet.GetXml()));
        }