]> git.lyx.org Git - lyx.git/blobdiff - src/LaTeX.cpp
Russian layouttranslations reviewed by Yuriy, Dec 13 2017.
[lyx.git] / src / LaTeX.cpp
index 24b44e9e3aa13bf54f2197d596975a80f7d9247e..79824217b81a2090b7c49b90932a968147097d6f 100644 (file)
@@ -58,7 +58,7 @@ docstring runMessage(unsigned int count)
        return bformat(_("Waiting for LaTeX run number %1$d"), count);
 }
 
-} // anon namespace
+} // namespace
 
 /*
  * CLASS TEXERRORS
@@ -93,9 +93,10 @@ bool operator!=(AuxInfo const & a, AuxInfo const & o)
  */
 
 LaTeX::LaTeX(string const & latex, OutputParams const & rp,
-            FileName const & f, string const & p, string const & lp,
-            bool const clean_start)
-       : cmd(latex), file(f), path(p), lpath(lp), runparams(rp), biber(false)
+            FileName const & f, string const & p, string const & lp, 
+            bool allow_cancellation, bool const clean_start)
+       : cmd(latex), file(f), path(p), lpath(lp), runparams(rp), biber(false),
+       allow_cancel(allow_cancellation)
 {
        num_errors = 0;
        // lualatex can still produce a DVI with --output-format=dvi. However,
@@ -244,12 +245,16 @@ int LaTeX::run(TeXErrors & terr)
        message(runMessage(count));
 
        int exit_code = startscript();
+       if (exit_code == Systemcall::KILLED)
+               return Systemcall::KILLED;
 
        scanres = scanLogFile(terr);
        if (scanres & ERROR_RERUN) {
                LYXERR(Debug::LATEX, "Rerunning LaTeX");
                terr.clearErrors();
                exit_code = startscript();
+               if (exit_code == Systemcall::KILLED)
+                       return Systemcall::KILLED;
                scanres = scanLogFile(terr);
        }
 
@@ -279,20 +284,34 @@ int LaTeX::run(TeXErrors & terr)
                LYXERR(Debug::LATEX, "Running MakeIndex.");
                message(_("Running Index Processor."));
                // onlyFileName() is needed for cygwin
-               rerun |= runMakeIndex(onlyFileName(idxfile.absFileName()),
-                               runparams);
+               int const ret = 
+                               runMakeIndex(onlyFileName(idxfile.absFileName()), runparams);
+               if (ret)
+                       return ret;
+               rerun = true;
        }
+
        FileName const nlofile(changeExtension(file.absFileName(), ".nlo"));
        // If all nomencl entries are removed, nomencl writes an empty nlo file.
        // DepTable::hasChanged() returns false in this case, since it does not
        // distinguish empty files from non-existing files. This is why we need
        // the extra checks here (to trigger a rerun). Cf. discussions in #8905.
        // FIXME: Sort out the real problem in DepTable.
-       if (head.haschanged(nlofile) || (nlofile.exists() && nlofile.isFileEmpty()))
-               rerun |= runMakeIndexNomencl(file, ".nlo", ".nls");
+       if (head.haschanged(nlofile) || (nlofile.exists() && nlofile.isFileEmpty())) {
+               int const ret = runMakeIndexNomencl(file, ".nlo", ".nls");
+               if (ret)
+                       return ret;
+               rerun = true;
+       }
+
        FileName const glofile(changeExtension(file.absFileName(), ".glo"));
-       if (head.haschanged(glofile))
-               rerun |= runMakeIndexNomencl(file, ".glo", ".gls");
+       if (head.haschanged(glofile)) {
+               int const ret = runMakeIndexNomencl(file, ".glo", ".gls");
+               if (ret)
+                       return ret;
+               rerun = true;
+       }
+
 
        // check if we're using biber instead of bibtex
        // biber writes no info to the aux file, so we just check
@@ -310,7 +329,10 @@ int LaTeX::run(TeXErrors & terr)
                LYXERR(Debug::LATEX, "Running BibTeX.");
                message(_("Running BibTeX."));
                updateBibtexDependencies(head, bibtex_info);
-               rerun |= runBibTeX(bibtex_info, runparams);
+               int exitCode;
+               rerun |= runBibTeX(bibtex_info, runparams, exitCode);
+               if (exitCode)
+                       return exitCode;
                FileName const blgfile(changeExtension(file.absFileName(), ".blg"));
                if (blgfile.exists())
                        bscanres = scanBlgFile(head, terr);
@@ -339,7 +361,9 @@ int LaTeX::run(TeXErrors & terr)
                LYXERR(Debug::DEPEND, "Dep. file has changed or rerun requested");
                LYXERR(Debug::LATEX, "Run #" << count);
                message(runMessage(count));
-               startscript();
+               int exitCode = startscript();
+               if (exitCode == Systemcall::KILLED)
+                       return Systemcall::KILLED;
                scanres = scanLogFile(terr);
 
                // update the depedencies
@@ -361,7 +385,10 @@ int LaTeX::run(TeXErrors & terr)
                LYXERR(Debug::LATEX, "Running BibTeX.");
                message(_("Running BibTeX."));
                updateBibtexDependencies(head, bibtex_info);
-               rerun |= runBibTeX(bibtex_info, runparams);
+               int exitCode;
+               rerun |= runBibTeX(bibtex_info, runparams, exitCode);
+               if (exitCode)
+                       return exitCode;
                FileName const blgfile(changeExtension(file.absFileName(), ".blg"));
                if (blgfile.exists())
                        bscanres = scanBlgFile(head, terr);
@@ -381,15 +408,19 @@ int LaTeX::run(TeXErrors & terr)
                LYXERR(Debug::LATEX, "Running MakeIndex.");
                message(_("Running Index Processor."));
                // onlyFileName() is needed for cygwin
-               rerun = runMakeIndex(onlyFileName(changeExtension(
+               int const ret = runMakeIndex(onlyFileName(changeExtension(
                                file.absFileName(), ".idx")), runparams);
+               if (ret)
+                       return ret;
+               rerun = true;
        }
 
        // I am not pretty sure if need this twice.
+       // MSVC complains that bool |= int is unsafe. Not sure why.
        if (head.haschanged(nlofile))
-               rerun |= runMakeIndexNomencl(file, ".nlo", ".nls");
+               rerun |= (runMakeIndexNomencl(file, ".nlo", ".nls") != 0);
        if (head.haschanged(glofile))
-               rerun |= runMakeIndexNomencl(file, ".glo", ".gls");
+               rerun |= (runMakeIndexNomencl(file, ".glo", ".gls") != 0);
 
        // 5
        // we will only run latex more if the log file asks for it.
@@ -442,11 +473,13 @@ int LaTeX::startscript()
                     + quoteName(onlyFileName(file.toFilesystemEncoding()))
                     + " > " + os::nulldev();
        Systemcall one;
-       return one.startscript(Systemcall::Wait, tmp, path, lpath);
+       Systemcall::Starttype const starttype = 
+               allow_cancel ? Systemcall::WaitLoop : Systemcall::Wait;
+       return one.startscript(starttype, tmp, path, lpath, true);
 }
 
 
-bool LaTeX::runMakeIndex(string const & f, OutputParams const & runparams,
+int LaTeX::runMakeIndex(string const & f, OutputParams const & runparams,
                         string const & params)
 {
        string tmp = runparams.use_japanese ?
@@ -469,12 +502,13 @@ bool LaTeX::runMakeIndex(string const & f, OutputParams const & runparams,
        tmp += quoteName(f);
        tmp += params;
        Systemcall one;
-       one.startscript(Systemcall::Wait, tmp, path, lpath);
-       return true;
+       Systemcall::Starttype const starttype = 
+               allow_cancel ? Systemcall::WaitLoop : Systemcall::Wait;
+       return one.startscript(starttype, tmp, path, lpath, true);
 }
 
 
-bool LaTeX::runMakeIndexNomencl(FileName const & file,
+int LaTeX::runMakeIndexNomencl(FileName const & file,
                string const & nlo, string const & nls)
 {
        LYXERR(Debug::LATEX, "Running MakeIndex for nomencl.");
@@ -485,8 +519,9 @@ bool LaTeX::runMakeIndexNomencl(FileName const & file,
        tmp += " -o "
                + onlyFileName(changeExtension(file.toFilesystemEncoding(), nls));
        Systemcall one;
-       one.startscript(Systemcall::Wait, tmp, path, lpath);
-       return true;
+       Systemcall::Starttype const starttype = 
+               allow_cancel ? Systemcall::WaitLoop : Systemcall::Wait;
+       return one.startscript(starttype, tmp, path, lpath, true);
 }
 
 
@@ -620,9 +655,10 @@ void LaTeX::updateBibtexDependencies(DepTable & dep,
 
 
 bool LaTeX::runBibTeX(vector<AuxInfo> const & bibtex_info,
-                     OutputParams const & runparams)
+                     OutputParams const & runparams, int & exit_code)
 {
        bool result = false;
+       exit_code = 0;
        for (vector<AuxInfo>::const_iterator it = bibtex_info.begin();
             it != bibtex_info.end(); ++it) {
                if (!biber && it->databases.empty())
@@ -635,7 +671,12 @@ bool LaTeX::runBibTeX(vector<AuxInfo> const & bibtex_info,
                tmp += quoteName(onlyFileName(removeExtension(
                                it->aux_file.absFileName())));
                Systemcall one;
-               one.startscript(Systemcall::Wait, tmp, path, lpath);
+               Systemcall::Starttype const starttype = 
+               allow_cancel ? Systemcall::WaitLoop : Systemcall::Wait;
+               exit_code = one.startscript(starttype, tmp, path, lpath, true);
+               if (exit_code) {
+                       return result;
+               }
        }
        // Return whether bibtex was run
        return result;
@@ -651,7 +692,7 @@ int LaTeX::scanLogFile(TeXErrors & terr)
                onlyFileName(changeExtension(file.absFileName(), ".log"));
        LYXERR(Debug::LATEX, "Log file: " << tmp);
        FileName const fn = FileName(makeAbsPath(tmp));
-       // FIXME we should use and ifdocstream here and a docstring for token
+       // FIXME we should use an ifdocstream here and a docstring for token
        // below. The encoding of the log file depends on the _output_ (font)
        // encoding of the TeX file (T1, TU etc.). See #10728.
        ifstream ifs(fn.toFilesystemEncoding().c_str());
@@ -936,11 +977,18 @@ int LaTeX::scanLogFile(TeXErrors & terr)
                                // Warning about missing glyph in selected font
                                // may be dataloss (bug 9610)
                                // but can be ignored for 'nullfont' (bug 10394).
-                               retval |= LATEX_ERROR;
-                               terr.insertError(0,
-                                                from_local8bit("Missing glyphs!"),
-                                                from_local8bit(token),
-                                                child_name);
+                               // as well as for ZERO WIDTH NON-JOINER (0x200C) which is
+                               // missing in many fonts and output for ligature break (bug 10727).
+                               // Since this error only occurs with utf8 output, we can safely assume
+                               // that the log file is utf8-encoded
+                               docstring const utoken = from_utf8(token);
+                               if (!contains(utoken, 0x200C)) {
+                                       retval |= LATEX_ERROR;
+                                       terr.insertError(0,
+                                                        from_ascii("Missing glyphs!"),
+                                                        utoken,
+                                                        child_name);
+                               }
                        } else if (!wait_for_error.empty()) {
                                // We collect information until we know we have an error.
                                wait_for_error += token + '\n';
@@ -1132,7 +1180,7 @@ int iterateLine(string const & token, regex const & reg, string const & closing,
        return result;
 }
 
-} // anon namespace
+} // namespace
 
 
 void LaTeX::deplog(DepTable & head)