77// ===----------------------------------------------------------------------===//
88
99#include " RPCCommon.h"
10+ #include " client/RPCLibraryHeaderEmitter.h"
11+ #include " client/RPCLibrarySourceEmitter.h"
1012#include " server/RPCServerHeaderEmitter.h"
1113#include " server/RPCServerSourceEmitter.h"
1214
@@ -46,6 +48,12 @@ static std::string GetServerOutputDirectory() {
4648 return std::string (Path);
4749}
4850
51+ static std::string GetLibraryOutputDirectory () {
52+ llvm::SmallString<256 > Path (OutputDir.getValue ());
53+ llvm::sys::path::append (Path, " lib" );
54+ return std::string (Path);
55+ }
56+
4957static std::unique_ptr<llvm::ToolOutputFile>
5058CreateOutputFile (llvm::StringRef OutputDir, llvm::StringRef Filename) {
5159 llvm::SmallString<256 > Path (OutputDir);
@@ -79,11 +87,14 @@ class SBVisitor : public RecursiveASTVisitor<SBVisitor> {
7987 SBVisitor (GeneratedByproducts &Byproducts, SourceManager &Manager,
8088 ASTContext &Context,
8189 std::unique_ptr<llvm::ToolOutputFile> &&ServerMethodOutputFile,
82- std::unique_ptr<llvm::ToolOutputFile> &&ServerHeaderOutputFile)
90+ std::unique_ptr<llvm::ToolOutputFile> &&ServerHeaderOutputFile,
91+ std::unique_ptr<llvm::ToolOutputFile> &&LibrarySourceOutputFile,
92+ std::unique_ptr<llvm::ToolOutputFile> &&LibraryHeaderOutputFile)
8393 : Byproducts(Byproducts), Manager(Manager), Context(Context),
8494 ServerSourceEmitter (std::move(ServerMethodOutputFile)),
85- ServerHeaderEmitter(std::move(ServerHeaderOutputFile)) {}
86-
95+ ServerHeaderEmitter(std::move(ServerHeaderOutputFile)),
96+ LibrarySourceEmitter(std::move(LibrarySourceOutputFile)),
97+ LibraryHeaderEmitter(std::move(LibraryHeaderOutputFile)) {}
8798 ~SBVisitor () {}
8899
89100 bool VisitCXXRecordDecl (CXXRecordDecl *RDecl) {
@@ -97,6 +108,12 @@ class SBVisitor : public RecursiveASTVisitor<SBVisitor> {
97108 PrintingPolicy Policy (Context.getLangOpts ());
98109 Policy.Bool = true ;
99110
111+ LibraryHeaderEmitter.StartClass (ClassName);
112+ LibrarySourceEmitter.StartClass (ClassName);
113+ for (Decl *D : RDecl->decls ())
114+ if (auto *E = dyn_cast_or_null<EnumDecl>(D))
115+ LibraryHeaderEmitter.EmitEnum (E);
116+
100117 for (CXXMethodDecl *MDecl : RDecl->methods ()) {
101118 const std::string MangledName =
102119 lldb_rpc_gen::GetMangledName (Context, MDecl);
@@ -107,10 +124,14 @@ class SBVisitor : public RecursiveASTVisitor<SBVisitor> {
107124 const lldb_rpc_gen::Method Method (MDecl, Policy, Context);
108125 ServerSourceEmitter.EmitMethod (Method);
109126 ServerHeaderEmitter.EmitMethod (Method);
127+ LibrarySourceEmitter.EmitMethod (Method);
128+ LibraryHeaderEmitter.EmitMethod (Method);
110129 Byproducts.MangledMethodNames .insert (MangledName);
111130 } else if (MethodSupportLevel == eUnimplemented)
112131 Byproducts.SkippedMethodNames .insert (MangledName);
113132 }
133+ LibraryHeaderEmitter.EndClass ();
134+ LibrarySourceEmitter.EndClass ();
114135 return true ;
115136 }
116137
@@ -210,16 +231,22 @@ class SBVisitor : public RecursiveASTVisitor<SBVisitor> {
210231 ASTContext &Context;
211232 lldb_rpc_gen::RPCServerSourceEmitter ServerSourceEmitter;
212233 lldb_rpc_gen::RPCServerHeaderEmitter ServerHeaderEmitter;
234+ lldb_rpc_gen::RPCLibrarySourceEmitter LibrarySourceEmitter;
235+ lldb_rpc_gen::RPCLibraryHeaderEmitter LibraryHeaderEmitter;
213236};
214237
215238class SBConsumer : public ASTConsumer {
216239public:
217240 SBConsumer (GeneratedByproducts &Byproducts, SourceManager &Manager,
218241 ASTContext &Context,
219242 std::unique_ptr<llvm::ToolOutputFile> &&ServerMethodOutputFile,
220- std::unique_ptr<llvm::ToolOutputFile> &&ServerHeaderOutputFile)
243+ std::unique_ptr<llvm::ToolOutputFile> &&ServerHeaderOutputFile,
244+ std::unique_ptr<llvm::ToolOutputFile> &&LibrarySourceOutputFile,
245+ std::unique_ptr<llvm::ToolOutputFile> &&LibraryHeaderOutputFile)
221246 : Visitor(Byproducts, Manager, Context, std::move(ServerMethodOutputFile),
222- std::move (ServerHeaderOutputFile)) {}
247+ std::move (ServerHeaderOutputFile),
248+ std::move(LibrarySourceOutputFile),
249+ std::move(LibraryHeaderOutputFile)) {}
223250 bool HandleTopLevelDecl (DeclGroupRef DR) override {
224251 for (Decl *D : DR)
225252 Visitor.TraverseDecl (D);
@@ -254,11 +281,26 @@ class SBAction : public ASTFrontendAction {
254281 if (!ServerHeaderOutputFile)
255282 return nullptr ;
256283
284+ const std::string LibrarySourceFilename = FilenameNoExt.str () + " .cpp" ;
285+ std::unique_ptr<llvm::ToolOutputFile> LibrarySourceOutputFile =
286+ CreateOutputFile (GetLibraryOutputDirectory (), LibrarySourceFilename);
287+ if (!LibrarySourceOutputFile)
288+ return nullptr ;
289+
290+ const std::string LibraryHeaderFilename = FilenameNoExt.str () + " .h" ;
291+ std::unique_ptr<llvm::ToolOutputFile> LibraryHeaderOutputFile =
292+ CreateOutputFile (GetLibraryOutputDirectory (), LibraryHeaderFilename);
293+ if (!LibraryHeaderOutputFile)
294+ return nullptr ;
295+
257296 ServerMethodOutputFile->keep ();
258297 ServerHeaderOutputFile->keep ();
298+ LibrarySourceOutputFile->keep ();
299+ LibraryHeaderOutputFile->keep ();
259300 return std::make_unique<SBConsumer>(
260301 Byproducts, CI.getSourceManager (), CI.getASTContext (),
261- std::move (ServerMethodOutputFile), std::move (ServerHeaderOutputFile));
302+ std::move (ServerMethodOutputFile), std::move (ServerHeaderOutputFile),
303+ std::move (LibrarySourceOutputFile), std::move (LibraryHeaderOutputFile));
262304 }
263305
264306private:
@@ -277,6 +319,8 @@ class SBActionFactory : public FrontendActionFactory {
277319 GeneratedByproducts &Byproducts;
278320};
279321
322+ // The amalgamated headers contain includes and RPC specific include guards for
323+ // the server and client side files. This is similar in usage to LLDB.h.
280324bool EmitAmalgamatedServerHeader (const std::vector<std::string> &Files) {
281325 // Create the file
282326 static constexpr llvm::StringLiteral AmalgamatedServerHeaderName = " SBAPI.h" ;
@@ -306,6 +350,28 @@ bool EmitAmalgamatedServerHeader(const std::vector<std::string> &Files) {
306350 return true ;
307351}
308352
353+ bool EmitAmalgamatedLibraryHeader (const std::vector<std::string> &Files) {
354+ static constexpr llvm::StringLiteral AmalgamatedLibraryHeaderName =
355+ " LLDBRPC.h" ;
356+ std::unique_ptr<llvm::ToolOutputFile> AmalgamatedLibraryHeader =
357+ CreateOutputFile (GetLibraryOutputDirectory (),
358+ AmalgamatedLibraryHeaderName);
359+ if (!AmalgamatedLibraryHeader)
360+ return false ;
361+
362+ AmalgamatedLibraryHeader->os () << " #ifndef LLDBRPC_H\n " ;
363+ AmalgamatedLibraryHeader->os () << " #define LLDBRPC_H\n " ;
364+ AmalgamatedLibraryHeader->os () << " #include \" SBLanguages.h\"\n " ;
365+ for (const auto &File : Files) {
366+ llvm::StringRef Filename = llvm::sys::path::filename (File);
367+ AmalgamatedLibraryHeader->os () << " #include \" " << Filename << " \"\n " ;
368+ }
369+
370+ AmalgamatedLibraryHeader->os () << " #endif // LLDBRPC_H\n " ;
371+ AmalgamatedLibraryHeader->keep ();
372+ return true ;
373+ }
374+
309375bool EmitClassNamesFile (std::set<std::string> &ClassNames) {
310376 static constexpr llvm::StringLiteral ClassNamesFileName = " SBClasses.def" ;
311377 std::unique_ptr<llvm::ToolOutputFile> ClassNamesFile =
@@ -387,6 +453,11 @@ int main(int argc, const char *argv[]) {
387453 if (!llvm::sys::fs::exists (GetServerOutputDirectory ())) {
388454 llvm::sys::fs::create_directory (GetServerOutputDirectory ());
389455 }
456+
457+ if (!llvm::sys::fs::exists (GetLibraryOutputDirectory ())) {
458+ llvm::sys::fs::create_directory (GetLibraryOutputDirectory ());
459+ }
460+
390461 CommonOptionsParser &OP = ExpectedParser.get ();
391462 auto PCHOpts = std::make_shared<PCHContainerOperations>();
392463 PCHOpts->registerWriter (std::make_unique<ObjectFilePCHContainerWriter>());
@@ -398,6 +469,10 @@ int main(int argc, const char *argv[]) {
398469 llvm::errs () << " Failed to create amalgamated server header\n " ;
399470 return 1 ;
400471 }
472+ if (!EmitAmalgamatedLibraryHeader (OP.getSourcePathList ())) {
473+ llvm::errs () << " Failed to create amalgamated library header\n " ;
474+ return 1 ;
475+ }
401476
402477 GeneratedByproducts Byproducts;
403478
0 commit comments