[Support] On Windows, generate PDF files for graphs and open with associated viewer

Summary: Windows system rarely have good PostScript viewers installed, but PDF viewers are common. So for viewing graphs, generate PDF files and open with the associated PDF viewer using cmd.exe's start command.

Reviewers: Bigcheese, aaron.ballman

Subscribers: aaron.ballman, JakeVanAdrighem, dwiberg, llvm-commits

Differential Revision: http://reviews.llvm.org/D11877

llvm-svn: 245290
This commit is contained in:
Michael Kruse 2015-08-18 12:17:37 +00:00
parent c0a8414c1c
commit c1c9f8a0d5
1 changed files with 49 additions and 23 deletions

View File

@ -189,61 +189,87 @@ bool llvm::DisplayGraph(StringRef FilenameRef, bool wait,
return ExecGraphViewer(ViewerPath, args, Filename, wait, ErrMsg);
}
enum PSViewerKind { PSV_None, PSV_OSXOpen, PSV_XDGOpen, PSV_Ghostview };
PSViewerKind PSViewer = PSV_None;
enum ViewerKind {
VK_None,
VK_OSXOpen,
VK_XDGOpen,
VK_Ghostview,
VK_CmdStart
};
ViewerKind Viewer = VK_None;
#ifdef __APPLE__
if (!PSViewer && S.TryFindProgram("open", ViewerPath))
PSViewer = PSV_OSXOpen;
if (!Viewer && S.TryFindProgram("open", ViewerPath))
Viewer = VK_OSXOpen;
#endif
if (!Viewer && S.TryFindProgram("gv", ViewerPath))
Viewer = VK_Ghostview;
if (!Viewer && S.TryFindProgram("xdg-open", ViewerPath))
Viewer = VK_XDGOpen;
#ifdef LLVM_ON_WIN32
if (!Viewer && S.TryFindProgram("cmd", ViewerPath)) {
Viewer = VK_CmdStart;
}
#endif
if (!PSViewer && S.TryFindProgram("gv", ViewerPath))
PSViewer = PSV_Ghostview;
if (!PSViewer && S.TryFindProgram("xdg-open", ViewerPath))
PSViewer = PSV_XDGOpen;
// PostScript graph generator + PostScript viewer
// PostScript or PDF graph generator + PostScript/PDF viewer
std::string GeneratorPath;
if (PSViewer &&
if (Viewer &&
(S.TryFindProgram(getProgramName(program), GeneratorPath) ||
S.TryFindProgram("dot|fdp|neato|twopi|circo", GeneratorPath))) {
std::string PSFilename = Filename + ".ps";
std::string OutputFilename =
Filename + (Viewer == VK_CmdStart ? ".pdf" : ".ps");
std::vector<const char *> args;
args.push_back(GeneratorPath.c_str());
args.push_back("-Tps");
if (Viewer == VK_CmdStart)
args.push_back("-Tpdf");
else
args.push_back("-Tps");
args.push_back("-Nfontname=Courier");
args.push_back("-Gsize=7.5,10");
args.push_back(Filename.c_str());
args.push_back("-o");
args.push_back(PSFilename.c_str());
args.push_back(OutputFilename.c_str());
args.push_back(nullptr);
errs() << "Running '" << GeneratorPath << "' program... ";
if (ExecGraphViewer(GeneratorPath, args, Filename, true, ErrMsg))
if (ExecGraphViewer(GeneratorPath, args, Filename, wait, ErrMsg))
return true;
// The lifetime of StartArg must include the call of ExecGraphViewer
// because the args are passed as vector of char*.
std::string StartArg;
args.clear();
args.push_back(ViewerPath.c_str());
switch (PSViewer) {
case PSV_OSXOpen:
switch (Viewer) {
case VK_OSXOpen:
args.push_back("-W");
args.push_back(PSFilename.c_str());
args.push_back(OutputFilename.c_str());
break;
case PSV_XDGOpen:
case VK_XDGOpen:
wait = false;
args.push_back(PSFilename.c_str());
args.push_back(OutputFilename.c_str());
break;
case PSV_Ghostview:
case VK_Ghostview:
args.push_back("--spartan");
args.push_back(PSFilename.c_str());
args.push_back(OutputFilename.c_str());
break;
case PSV_None:
case VK_CmdStart:
args.push_back("/S");
args.push_back("/C");
StartArg =
(StringRef("start ") + (wait ? "/WAIT " : "") + OutputFilename).str();
args.push_back(StartArg.c_str());
break;
case VK_None:
llvm_unreachable("Invalid viewer");
}
args.push_back(nullptr);
ErrMsg.clear();
return ExecGraphViewer(ViewerPath, args, PSFilename, wait, ErrMsg);
return ExecGraphViewer(ViewerPath, args, OutputFilename, wait, ErrMsg);
}
// dotty