Exemple #1
0
void HeaderSearchDirs::addSearchDirs ( std::vector<std::string> & include_dirs ) {
    AddUserSearchDirs( include_dirs ) ;
    AddTrickSearchDirs() ;
    AddCompilerBuiltInSearchDirs() ;
    AddExcludeDirs() ;
    AddICGExcludeDirs() ;
    AddICGNoCommentDirs() ;
    ApplyHeaderSearchOptions() ;
}
Exemple #2
0
    bool parse(Component& component, Module* existingMod, const std::string& filename, bool printAST) {
        // NOTE: seems to get deleted by Preprocessor
        HeaderSearch* Headers = new HeaderSearch(HSOpts, SM, Diags, LangOpts, pti);
        DummyLoader loader;

        std::shared_ptr<PreprocessorOptions> PPOpts(new PreprocessorOptions());
        Preprocessor PP(PPOpts, Diags, LangOpts, SM, *Headers, loader);

        ApplyHeaderSearchOptions(PP.getHeaderSearchInfo(), *HSOpts, LangOpts, pti->getTriple());
        PP.setPredefines(configs);
        PP.Initialize(*pti);

        // File stuff
        const FileEntry *pFile = FileMgr.getFile(filename);
        if (pFile == 0) {
            fprintf(stderr, "Error opening file: '%s'\n", filename.c_str());
            exit(-1);
        }
        FileID id = SM.createFileID(pFile, SourceLocation(), SrcMgr::C_User);
        PP.EnterSourceFile(id, nullptr, SourceLocation());

        // TEMP rewriter test
        //ast.fileID = id;
        // Manually set predefines (normally done in EnterMainSourceFile())
        std::unique_ptr<llvm::MemoryBuffer> SB = llvm::MemoryBuffer::getMemBufferCopy(configs, "<built-in>");
        assert(SB && "Cannot create predefined source buffer");
        FileID FID = SM.createFileID(std::move(SB));

        // NOTE: setPredefines() is normally private
        PP.setPredefinesFileID(FID);
        PP.EnterSourceFile(FID, nullptr, SourceLocation());

        Diags.getClient()->BeginSourceFile(LangOpts, 0);

        C2Sema sema(SM, Diags, PP, component, existingMod, filename);
        C2Parser parser(PP, sema, component.isExternal());
        bool ok = parser.Parse();
        if (printAST) sema.printAST();
#if 0
        PP.EndSourceFile();

        llvm::errs() << "\nSTATISTICS FOR '" << ast.getFileName() << "':\n";
        PP.PrintStats();
        PP.getIdentifierTable().PrintStats();
        llvm::errs() << "\n";
#endif
        return ok;
    }
ExpandModularHeadersPPCallbacks::ExpandModularHeadersPPCallbacks(
    CompilerInstance *CI,
    IntrusiveRefCntPtr<llvm::vfs::OverlayFileSystem> OverlayFS)
    : Recorder(llvm::make_unique<FileRecorder>()), Compiler(*CI),
      InMemoryFs(new llvm::vfs::InMemoryFileSystem),
      Sources(Compiler.getSourceManager()),
      // Forward the new diagnostics to the original DiagnosticConsumer.
      Diags(new DiagnosticIDs, new DiagnosticOptions,
            new ForwardingDiagnosticConsumer(Compiler.getDiagnosticClient())),
      LangOpts(Compiler.getLangOpts()) {
  // Add a FileSystem containing the extra files needed in place of modular
  // headers.
  OverlayFS->pushOverlay(InMemoryFs);

  Diags.setSourceManager(&Sources);

  LangOpts.Modules = false;

  auto HSO = std::make_shared<HeaderSearchOptions>();
  *HSO = Compiler.getHeaderSearchOpts();

  HeaderInfo = llvm::make_unique<HeaderSearch>(HSO, Sources, Diags, LangOpts,
                                               &Compiler.getTarget());

  auto PO = std::make_shared<PreprocessorOptions>();
  *PO = Compiler.getPreprocessorOpts();

  PP = llvm::make_unique<clang::Preprocessor>(PO, Diags, LangOpts, Sources,
                                              *HeaderInfo, ModuleLoader,
                                              /*IILookup=*/nullptr,
                                              /*OwnsHeaderSearch=*/false);
  PP->Initialize(Compiler.getTarget(), Compiler.getAuxTarget());
  InitializePreprocessor(*PP, *PO, Compiler.getPCHContainerReader(),
                         Compiler.getFrontendOpts());
  ApplyHeaderSearchOptions(*HeaderInfo, *HSO, LangOpts,
                           Compiler.getTarget().getTriple());
}
std::vector<std::string> getLocalizedStringFromFile(std::string filename, std::string triple, std::vector<std::string> includepaths)
{
    clang::DiagnosticOptions diagnosticOptions;

#if LLVM_VERSION_MAJOR == 3 && LLVM_VERSION_MINOR >= 2
    clang::TextDiagnosticPrinter *pTextDiagnosticPrinter =
        new clang::TextDiagnosticPrinter(
            llvm::outs(), &diagnosticOptions);
#else 
    clang::TextDiagnosticPrinter *pTextDiagnosticPrinter =
        new clang::TextDiagnosticPrinter(
            llvm::outs(), diagnosticOptions);
#endif
    llvm::IntrusiveRefCntPtr<clang::DiagnosticIDs> pDiagIDs;
#if LLVM_VERSION_MAJOR == 3 && LLVM_VERSION_MINOR >= 2 
    clang::DiagnosticsEngine *pDiagnosticsEngine =
        new clang::DiagnosticsEngine(pDiagIDs,
            &diagnosticOptions,
            pTextDiagnosticPrinter);
#else
    clang::DiagnosticsEngine *pDiagnosticsEngine =
        new clang::DiagnosticsEngine(pDiagIDs,
            pTextDiagnosticPrinter);
#endif

    clang::LangOptions languageOptions;
    clang::FileSystemOptions fileSystemOptions;
    clang::FileManager fileManager(fileSystemOptions);

    clang::SourceManager sourceManager(
        *pDiagnosticsEngine,
        fileManager);

    clang::TargetOptions targetOptions;
    targetOptions.Triple = triple;//"arm-apple-darwin11";//llvm::sys::getDefaultTargetTriple();
#if LLVM_VERSION_MAJOR == 3 && LLVM_VERSION_MINOR >= 2 
    clang::TargetInfo *pTargetInfo = 
        clang::TargetInfo::CreateTargetInfo(
            *pDiagnosticsEngine,
#if LLVM_VERSION_MAJOR == 3 && LLVM_VERSION_MINOR == 2
            targetOptions
#else
            &targetOptions
#endif
            );   
    llvm::IntrusiveRefCntPtr<clang::HeaderSearchOptions> headerSearchOptions(new clang::HeaderSearchOptions());
    for(int i = 0 ; i < includepaths.size(); i++)
        headerSearchOptions->AddPath(includepaths.at(i),
                clang::frontend::Angled,
                false,
#if LLVM_VERSION_MAJOR == 3 && LLVM_VERSION_MINOR == 2 
		false,
		false,
		false,
#endif
                false);
    clang::HeaderSearch headerSearch(headerSearchOptions,
                                     fileManager,
                                     *pDiagnosticsEngine,
                                     languageOptions,
                                     pTargetInfo);
#else
    clang::TargetInfo *pTargetInfo =
        clang::TargetInfo::CreateTargetInfo(
            *pDiagnosticsEngine,
            targetOptions);
    clang::HeaderSearchOptions headerSearchOptions;
    for(int i = 0 ; i < includepaths.size(); i++)
        headerSearchOptions.AddPath(includepaths.at(i),
                clang::frontend::Angled,
                false,
                false,
                false);
    clang::HeaderSearch headerSearch(fileManager,
                                     *pDiagnosticsEngine,
                                     languageOptions,
                                     pTargetInfo);
    ApplyHeaderSearchOptions(headerSearch, headerSearchOptions, languageOptions, pTargetInfo->getTriple());
#endif

/*    headerSearchOptions->AddPath("/usr/share/iPhoneOS5.0.sdk/usr/include/c++/4.2.1/tr1/",
            clang::frontend::Angled,
            false,
            false,
            false);
    headerSearchOptions->AddPath("/usr/share/iPhoneOS5.0.sdk/usr/include/c++/4.2.1",
            clang::frontend::Angled,
            false,
            false,
            false);
*/
    clang::CompilerInstance compInst;

#if LLVM_VERSION_MAJOR == 3 && LLVM_VERSION_MINOR >=2
    llvm::IntrusiveRefCntPtr<clang::PreprocessorOptions> pOpts (new clang::PreprocessorOptions());
    clang::Preprocessor preprocessor(
        pOpts,
        *pDiagnosticsEngine,
        languageOptions,
        pTargetInfo,
        sourceManager,
        headerSearch,
        compInst);
   clang::FrontendOptions frontendOptions;
   clang::InitializePreprocessor(
        preprocessor,
        *pOpts,
        *headerSearchOptions,
        frontendOptions);

#else
    clang::PreprocessorOptions pOpts;

    clang::Preprocessor preprocessor(
        *pDiagnosticsEngine,
        languageOptions,
        pTargetInfo,
        sourceManager,
        headerSearch,
        compInst);

   clang::FrontendOptions frontendOptions;
   clang::InitializePreprocessor(
        preprocessor,
        pOpts,
        headerSearchOptions,
        frontendOptions);
#endif


    const clang::FileEntry *pFile = fileManager.getFile(filename);
    sourceManager.createMainFileID(pFile);
    preprocessor.EnterMainSourceFile();
    pTextDiagnosticPrinter->BeginSourceFile(languageOptions, &preprocessor);

/*
 * identifier 'localizedStringForKey'
 * colon ':'
 * l_paren '('
 * unknown '@'
 * string_literal '"UIAlertView"'
 * r_paren ')'
 *
*/

    int found = 0;
    std::string trans_str;
    std::vector<std::string> trans_list;
    clang::Token token;
    do {
        preprocessor.Lex(token);
        if( pDiagnosticsEngine->hasErrorOccurred())
        {
            break;
        }
        // if we meet localizedStringForKey, that means we need record it params.
        if(token.is(clang::tok::identifier) && token.isNot(clang::tok::raw_identifier)) {
            const clang::IdentifierInfo *II = token.getIdentifierInfo();
            if ( II && (strcmp(II->getName().data(), "localizedStringForKey") == 0))
                found = 1;
        }

        // only string literal we should handle.
        if(found == 1 && token.is(clang::tok::string_literal)) {
               std::string got = preprocessor.getSpelling(token); //here, we got a string with "" 
               got = got.substr(1,got.length()-2); //remove ""
               trans_str += got; // string may split to multiline, we save them all.
        }
        // when match ), that means we got what we need.
        // push it to vector and wait next found == 1;
        if(found == 1 && token.is(clang::tok::r_paren) && token.isNot(clang::tok::raw_identifier)) {
            trans_list.push_back(trans_str);
            trans_str.clear();            
            found = 0;
        }
    } while( token.isNot(clang::tok::eof));
    pTextDiagnosticPrinter->EndSourceFile();

    /*for(int i = 0; i < trans_list.size(); i++)
        std::cout<<trans_list[i]<<std::endl;
    */
    return trans_list;
}
int main(int argc, const char **argv, char * const *envp)
{
    // Path
    void *MainAddr = (void*) (intptr_t) GetExecutablePath;
    llvm::sys::Path Path = GetExecutablePath(argv[0]);

    // DiagnosticOptions
    DiagnosticOptions diagnosticOptions;

    // DiagnosticClient
    TextDiagnosticPrinter *DiagClient = new TextDiagnosticPrinter(llvm::outs(), diagnosticOptions);

    // Diagnostic
    llvm::IntrusiveRefCntPtr<DiagnosticIDs> DiagID(new DiagnosticIDs());
    Diagnostic diagnostic(DiagID, DiagClient);


    //DiagnosticOptions DiagOpts;
    //llvm::IntrusiveRefCntPtr<Diagnostic> diagnostic = CompilerInstance::createDiagnostics(DiagOpts, argc, argv);

    // LangOptions
    LangOptions langOptions;
    langOptions.CPlusPlus = 1;
    langOptions.CPlusPlus0x = 1;
    langOptions.Microsoft = 1;
    langOptions.Bool = 1;
    langOptions.Exceptions = 1;
    langOptions.CXXExceptions = 1;
    langOptions.EmitAllDecls = 1;

    // FileManager
    FileSystemOptions fileSystemOptions;
    FileManager fileManager(fileSystemOptions);

    // SourceManager
    SourceManager sourceManager(diagnostic, fileManager);

    // HeadderSearch
    HeaderSearch headerSearch(fileManager);

    // TargetOptions
    TargetOptions targetOptions;
    targetOptions.Triple = llvm::sys::getHostTriple();

    // TargetInfo
    TargetInfo *pTargetInfo =
        TargetInfo::CreateTargetInfo(
            diagnostic,
            targetOptions);

    // HeaderSearchOptions
    HeaderSearchOptions headerSearchOptions;
    ApplyHeaderSearchOptions(
        headerSearch,
        headerSearchOptions,
        langOptions,
        pTargetInfo->getTriple());

    // Preprocessor
    Preprocessor preprocessor(
        diagnostic,
        langOptions,
        *pTargetInfo,
        sourceManager,
        headerSearch);

    // PreprocessorOptions
    PreprocessorOptions preprocessorOptions;
    preprocessorOptions.DetailedRecord = true;
    preprocessor.createPreprocessingRecord();

    // FrontendOptions
    FrontendOptions frontendOptions;


    // InitializePreprocessor
    InitializePreprocessor(
        preprocessor,
        preprocessorOptions,
        headerSearchOptions,
        frontendOptions);

    //preprocessor.SetCommentRetentionState(true, true);

    // Tutorial
    const FileEntry *pFile = fileManager.getFile(
                                 "test.cpp",
                                 true);
    sourceManager.createMainFileID(pFile);


    /*preprocessor.EnterMainSourceFile();
    Token Tok;
    do {
    	preprocessor.Lex(Tok);  // read one token
    	//if (context.diags.hasErrorOccurred())  // stop lexing/pp on error
    	//	break;
    	preprocessor.DumpToken(Tok);  // outputs to cerr
    	std::cerr << std::endl;
    } while (Tok.isNot(tok::eof));*/


    const TargetInfo &targetInfo = *pTargetInfo;

    IdentifierTable identifierTable(langOptions);
    SelectorTable selectorTable;

    Builtin::Context builtinContext(targetInfo);
    ASTContext astContext(
        langOptions,
        sourceManager,
        targetInfo,
        identifierTable,
        selectorTable,
        builtinContext,
        0 /* size_reserve*/);
    // ASTConsumer astConsumer;
    MyASTConsumer astConsumer;
    astConsumer.sourceManager = &sourceManager;
    astConsumer.html = new ClangDocHTML;
    astConsumer.html->astConsumer = &astConsumer;
    preprocessor.addPPCallbacks(astConsumer.html);
    preprocessor.AddCommentHandler(astConsumer.html);

    Sema sema(
        preprocessor,
        astContext,
        astConsumer);
    sema.Initialize();

    //MySemanticAnalisys mySema( preprocessor, astContext, astConsumer);

    //Parser parser( preprocessor, sema);
    //parser.ParseTranslationUnit();
    astConsumer.preprocessor = &sema.PP;
    ParseAST(preprocessor, &astConsumer, astContext);
    return 0;
}