Пример #1
0
void
Win32MakefileGenerator::processPrlFiles()
{
    const QString libArg = project->first("QMAKE_L_FLAG").toQString();
    QList<QMakeLocalFileName> libdirs;
    static const char * const lflags[] = { "QMAKE_LIBS", "QMAKE_LIBS_PRIVATE", 0 };
    for (int i = 0; lflags[i]; i++) {
        ProStringList &l = project->values(lflags[i]);
        for (int lit = 0; lit < l.size(); ++lit) {
            QString opt = l.at(lit).trimmed().toQString();
            if((opt[0] == '\'' || opt[0] == '"') && opt[(int)opt.length()-1] == opt[0])
                opt = opt.mid(1, opt.length()-2);
            if (opt.startsWith(libArg)) {
                QMakeLocalFileName l(opt.mid(libArg.length()));
                if (!libdirs.contains(l))
                    libdirs.append(l);
            } else if (!opt.startsWith("/")) {
                if (!processPrlFile(opt) && (QDir::isRelativePath(opt) || opt.startsWith("-l"))) {
                    QString tmp;
                    if (opt.startsWith("-l"))
                        tmp = opt.mid(2);
                    else
                        tmp = opt;
                    for(QList<QMakeLocalFileName>::Iterator it = libdirs.begin(); it != libdirs.end(); ++it) {
                        QString prl = (*it).local() + Option::dir_sep + tmp;
                        if (processPrlFile(prl))
                            break;
                    }
                }
            }
            ProStringList &prl_libs = project->values("QMAKE_CURRENT_PRL_LIBS");
            for (int prl = 0; prl < prl_libs.size(); ++prl) {
                ProString arg = prl_libs.at(prl);
                if (arg.startsWith(libArg))
                    arg = arg.left(libArg.length()) + escapeFilePath(arg.mid(libArg.length()).toQString());
                else if (!arg.startsWith('/'))
                    arg = escapeFilePath(arg.toQString());
                l.insert(lit + prl + 1, arg);
            }
            prl_libs.clear();
        }

        // Merge them into a logical order
        if (!project->isActiveConfig("no_smart_library_merge") && !project->isActiveConfig("no_lflags_merge")) {
            ProStringList lflags;
            for (int lit = 0; lit < l.size(); ++lit) {
                ProString opt = l.at(lit).trimmed();
                if (opt.startsWith(libArg)) {
                    if (!lflags.contains(opt))
                        lflags.append(opt);
                } else {
                    // Make sure we keep the dependency-order of libraries
                    lflags.removeAll(opt);
                    lflags.append(opt);
                }
            }
            l = lflags;
        }
    }
}
void MingwMakefileGenerator::writeIncPart(QTextStream &t)
{
    t << "INCPATH       = ";

    if (!project->isActiveConfig("no_include_pwd")) {
        QString pwd = escapeFilePath(fileFixify(qmake_getpwd()));
        if (pwd.isEmpty())
            pwd = ".";
        t << "-I" << pwd << " ";
    }

    QString isystem = var("QMAKE_CFLAGS_ISYSTEM");
    const ProStringList &incs = project->values("INCLUDEPATH");
    for (ProStringList::ConstIterator incit = incs.begin(); incit != incs.end(); ++incit) {
        QString inc = (*incit).toQString();
        inc.replace(QRegExp("\\\\$"), "");
        inc.replace(QRegExp("\""), "");

        if (!isystem.isEmpty() && isSystemInclude(inc))
            t << isystem << ' ';
        else
            t << "-I";
        t << quote << inc << quote << " ";
    }
    t << "-I" << quote << specdir() << quote
      << endl;
}
Пример #3
0
void MingwMakefileGenerator::writeObjectsPart(QTextStream &t)
{
    if (project->values("OBJECTS").count() < var("QMAKE_LINK_OBJECT_MAX").toInt()) {
        objectsLinkLine = "$(OBJECTS)";
    } else if (project->isActiveConfig("staticlib") && project->first("TEMPLATE") == "lib") {
	QString ar_script_file = var("QMAKE_LINK_OBJECT_SCRIPT") + "." + var("TARGET");
	if (!var("BUILD_NAME").isEmpty()) {
	    ar_script_file += "." + var("BUILD_NAME");
	}
        // QMAKE_LIB is used for win32, including mingw, whereas QMAKE_AR is used on Unix.
        if (project->isActiveConfig("rvct_linker")) {
            createRvctObjectScriptFile(ar_script_file, project->values("OBJECTS"));
            QString ar_cmd = project->values("QMAKE_LIB").join(' ');
            if (ar_cmd.isEmpty())
                ar_cmd = "armar --create";
            objectsLinkLine = ar_cmd + " " + var("DEST_TARGET") + " --via " + escapeFilePath(ar_script_file);
        } else {
            // Strip off any options since the ar commands will be read from file.
            QString ar_cmd = var("QMAKE_LIB").section(" ", 0, 0);;
            if (ar_cmd.isEmpty())
                ar_cmd = "ar";
            createArObjectScriptFile(ar_script_file, var("DEST_TARGET"), project->values("OBJECTS"));
            objectsLinkLine = ar_cmd + " -M < " + escapeFilePath(ar_script_file);
        }
    } else {
        QString ld_script_file = var("QMAKE_LINK_OBJECT_SCRIPT") + "." + var("TARGET");
	if (!var("BUILD_NAME").isEmpty()) {
	    ld_script_file += "." + var("BUILD_NAME");
	}
        if (project->isActiveConfig("rvct_linker")) {
            createRvctObjectScriptFile(ld_script_file, project->values("OBJECTS"));
            objectsLinkLine = QString::fromLatin1("--via ") + escapeFilePath(ld_script_file);
        } else {
            createLdObjectScriptFile(ld_script_file, project->values("OBJECTS"));
            objectsLinkLine = escapeFilePath(ld_script_file);
        }
    }
    Win32MakefileGenerator::writeObjectsPart(t);
}
void MingwMakefileGenerator::writeRcFilePart(QTextStream &t)
{
    const QString rc_file = fileFixify(project->first("RC_FILE").toQString());

    ProStringList rcIncPaths = project->values("RC_INCLUDEPATH");
    rcIncPaths.prepend(fileInfo(rc_file).path());
    QString incPathStr;
    for (int i = 0; i < rcIncPaths.count(); ++i) {
        const ProString &path = rcIncPaths.at(i);
        if (path.isEmpty())
            continue;
        incPathStr += QStringLiteral(" --include-dir=");
        if (path != "." && QDir::isRelativePath(path.toQString()))
            incPathStr += "./";
        incPathStr += escapeFilePath(path);
    }

    if (!rc_file.isEmpty()) {
        t << escapeDependencyPath(var("RES_FILE")) << ": " << rc_file << "\n\t"
          << var("QMAKE_RC") << " -i " << rc_file << " -o " << var("RES_FILE")
          << incPathStr << " $(DEFINES)\n\n";
    }
}
Пример #5
0
void Win32MakefileGenerator::writeStandardParts(QTextStream &t)
{
    t << "####### Compiler, tools and options" << endl << endl;
    t << "CC            = " << var("QMAKE_CC") << endl;
    t << "CXX           = " << var("QMAKE_CXX") << endl;
    t << "DEFINES       = "
      << varGlue("PRL_EXPORT_DEFINES","-D"," -D"," ")
      << varGlue("DEFINES","-D"," -D","") << endl;
    t << "CFLAGS        = " << var("QMAKE_CFLAGS") << " $(DEFINES)" << endl;
    t << "CXXFLAGS      = " << var("QMAKE_CXXFLAGS") << " $(DEFINES)" << endl;

    writeIncPart(t);
    writeLibsPart(t);

    t << "QMAKE         = " << var("QMAKE_QMAKE") << endl;
    t << "IDC           = " << (project->isEmpty("QMAKE_IDC") ? QString("idc") :
                              Option::fixPathToTargetOS(var("QMAKE_IDC"), false)) << endl;
    t << "IDL           = " << (project->isEmpty("QMAKE_IDL") ? QString("midl") :
                              Option::fixPathToTargetOS(var("QMAKE_IDL"), false)) << endl;
    t << "ZIP           = " << var("QMAKE_ZIP") << endl;
    t << "DEF_FILE      = " << varList("DEF_FILE") << endl;
    t << "RES_FILE      = " << varList("RES_FILE") << endl; // Not on mingw, can't see why not though...
    t << "COPY          = " << var("QMAKE_COPY") << endl;
    t << "SED           = " << var("QMAKE_STREAM_EDITOR") << endl;
    t << "COPY_FILE     = " << var("QMAKE_COPY_FILE") << endl;
    t << "COPY_DIR      = " << var("QMAKE_COPY_DIR") << endl;
    t << "DEL_FILE      = " << var("QMAKE_DEL_FILE") << endl;
    t << "DEL_DIR       = " << var("QMAKE_DEL_DIR") << endl;
    t << "MOVE          = " << var("QMAKE_MOVE") << endl;
    t << "CHK_DIR_EXISTS= " << var("QMAKE_CHK_DIR_EXISTS") << endl;
    t << "MKDIR         = " << var("QMAKE_MKDIR") << endl;
    t << "INSTALL_FILE    = " << var("QMAKE_INSTALL_FILE") << endl;
    t << "INSTALL_PROGRAM = " << var("QMAKE_INSTALL_PROGRAM") << endl;
    t << "INSTALL_DIR     = " << var("QMAKE_INSTALL_DIR") << endl;
    t << endl;

    t << "####### Output directory" << endl << endl;
    if(!project->values("OBJECTS_DIR").isEmpty())
        t << "OBJECTS_DIR   = " << var("OBJECTS_DIR").replace(QRegExp("\\\\$"),"") << endl;
    else
        t << "OBJECTS_DIR   = . " << endl;
    t << endl;

    t << "####### Files" << endl << endl;
    t << "SOURCES       = " << valList(escapeFilePaths(project->values("SOURCES")))
      << " " << valList(escapeFilePaths(project->values("GENERATED_SOURCES"))) << endl;

    // do this here so we can set DEST_TARGET to be the complete path to the final target if it is needed.
    QString orgDestDir = var("DESTDIR");
    QString destDir = Option::fixPathToTargetOS(orgDestDir, false);
    if (!destDir.isEmpty() && (orgDestDir.endsWith('/') || orgDestDir.endsWith(Option::dir_sep)))
        destDir += Option::dir_sep;
    QString target = QString(project->first("TARGET")+project->first("TARGET_EXT"));
    target.remove("\"");
    project->values("DEST_TARGET").prepend(destDir + target);

    writeObjectsPart(t);

    writeExtraCompilerVariables(t);
    writeExtraVariables(t);

    t << "DIST          = " << varList("DISTFILES") << endl;
    t << "QMAKE_TARGET  = " << var("QMAKE_ORIG_TARGET") << endl;
    // The comment is important to maintain variable compatibility with Unix
    // Makefiles, while not interpreting a trailing-slash as a linebreak
    t << "DESTDIR        = " << escapeFilePath(destDir) << " #avoid trailing-slash linebreak" << endl;
    t << "TARGET         = " << escapeFilePath(target) << endl;
    t << "DESTDIR_TARGET = " << escapeFilePath(var("DEST_TARGET")) << endl;
    t << endl;

    t << "####### Implicit rules" << endl << endl;
    writeImplicitRulesPart(t);

    t << "####### Build rules" << endl << endl;
    writeBuildRulesPart(t);

    if(project->isActiveConfig("shared") && !project->values("DLLDESTDIR").isEmpty()) {
        QStringList dlldirs = project->values("DLLDESTDIR");
        for (QStringList::Iterator dlldir = dlldirs.begin(); dlldir != dlldirs.end(); ++dlldir) {
            t << "\t" << "-$(COPY_FILE) \"$(DESTDIR_TARGET)\" " << Option::fixPathToTargetOS(*dlldir, false) << endl;
        }
    }
    t << endl;

    writeRcFilePart(t);

    writeMakeQmake(t);

    QStringList dist_files = fileFixify(Option::mkfile::project_files);
    if(!project->isEmpty("QMAKE_INTERNAL_INCLUDED_FILES"))
        dist_files += project->values("QMAKE_INTERNAL_INCLUDED_FILES");
    if(!project->isEmpty("TRANSLATIONS"))
        dist_files << var("TRANSLATIONS");
    if(!project->isEmpty("FORMS")) {
        QStringList &forms = project->values("FORMS");
        for(QStringList::Iterator formit = forms.begin(); formit != forms.end(); ++formit) {
            QString ui_h = fileFixify((*formit) + Option::h_ext.first());
            if(exists(ui_h))
                dist_files << ui_h;
        }
    }
    t << "dist:" << "\n\t"
      << "$(ZIP) " << var("QMAKE_ORIG_TARGET") << ".zip " << "$(SOURCES) $(DIST) "
      << dist_files.join(" ") << " " << var("TRANSLATIONS") << " ";
    if(!project->isEmpty("QMAKE_EXTRA_COMPILERS")) {
        const QStringList &quc = project->values("QMAKE_EXTRA_COMPILERS");
        for(QStringList::ConstIterator it = quc.begin(); it != quc.end(); ++it) {
            const QStringList &inputs = project->values((*it)+".input");
            for(QStringList::ConstIterator input = inputs.begin(); input != inputs.end(); ++input) {
                t << (*input) << " ";
            }
        }
    }
    t << endl << endl;

    writeCleanParts(t);
    writeExtraTargets(t);
    writeExtraCompilerTargets(t);
    t << endl << endl;
}
Пример #6
0
void Win32MakefileGenerator::writeCleanParts(QTextStream &t)
{
    t << "clean: compiler_clean " << var("CLEAN_DEPS");
    {
        const char *clean_targets[] = { "OBJECTS", "QMAKE_CLEAN", "CLEAN_FILES", 0 };
        for(int i = 0; clean_targets[i]; ++i) {
            const QStringList &list = project->values(clean_targets[i]);
            const QString del_statement("-$(DEL_FILE)");
            if(project->isActiveConfig("no_delete_multiple_files")) {
                for(QStringList::ConstIterator it = list.begin(); it != list.end(); ++it)
                    t << "\n\t" << del_statement << " " << escapeFilePath((*it));
            } else {
                QString files, file;
                const int commandlineLimit = 2047; // NT limit, expanded
                for(QStringList::ConstIterator it = list.begin(); it != list.end(); ++it) {
                    file = " " + escapeFilePath((*it));
                    if(del_statement.length() + files.length() +
                       qMax(fixEnvVariables(file).length(), file.length()) > commandlineLimit) {
                        t << "\n\t" << del_statement << files;
                        files.clear();
                    }
                    files += file;
                }
                if(!files.isEmpty())
                    t << "\n\t" << del_statement << files;
            }
        }
    }
    t << endl << endl;

    t << "distclean: clean";
    {
        const char *clean_targets[] = { "QMAKE_DISTCLEAN", 0 };
        for(int i = 0; clean_targets[i]; ++i) {
            const QStringList &list = project->values(clean_targets[i]);
            const QString del_statement("-$(DEL_FILE)");
            if(project->isActiveConfig("no_delete_multiple_files")) {
                for(QStringList::ConstIterator it = list.begin(); it != list.end(); ++it)
                    t << "\n\t" << del_statement << " " << escapeFilePath((*it));
            } else {
                QString files, file;
                const int commandlineLimit = 2047; // NT limit, expanded
                for(QStringList::ConstIterator it = list.begin(); it != list.end(); ++it) {
                    file = " " + escapeFilePath((*it));
                    if(del_statement.length() + files.length() +
                       qMax(fixEnvVariables(file).length(), file.length()) > commandlineLimit) {
                        t << "\n\t" << del_statement << files;
                        files.clear();
                    }
                    files += file;
                }
                if(!files.isEmpty())
                    t << "\n\t" << del_statement << files;
            }
        }
    }
    t << "\n\t-$(DEL_FILE) $(DESTDIR_TARGET)" << endl;
    {
        QString ofile = Option::fixPathToTargetOS(fileFixify(Option::output.fileName()));
        if(!ofile.isEmpty())
            t << "\t-$(DEL_FILE) " << ofile << endl;
    }
    t << endl;
}
Пример #7
0
void MingwMakefileGenerator::init()
{
    if(init_flag)
        return;
    init_flag = true;

    /* this should probably not be here, but I'm using it to wrap the .t files */
    if(project->first("TEMPLATE") == "app")
        project->values("QMAKE_APP_FLAG").append("1");
    else if(project->first("TEMPLATE") == "lib")
        project->values("QMAKE_LIB_FLAG").append("1");
    else if(project->first("TEMPLATE") == "subdirs") {
        MakefileGenerator::init();
        if(project->isEmpty("QMAKE_COPY_FILE"))
            project->values("QMAKE_COPY_FILE").append("$(COPY)");
        if(project->isEmpty("QMAKE_COPY_DIR"))
            project->values("QMAKE_COPY_DIR").append("xcopy /s /q /y /i");
        if(project->isEmpty("QMAKE_INSTALL_FILE"))
            project->values("QMAKE_INSTALL_FILE").append("$(COPY_FILE)");
        if(project->isEmpty("QMAKE_INSTALL_PROGRAM"))
            project->values("QMAKE_INSTALL_PROGRAM").append("$(COPY_FILE)");
        if(project->isEmpty("QMAKE_INSTALL_DIR"))
            project->values("QMAKE_INSTALL_DIR").append("$(COPY_DIR)");
        if(project->values("MAKEFILE").isEmpty())
            project->values("MAKEFILE").append("Makefile");
        return;
    }

    project->values("TARGET_PRL").append(project->first("TARGET"));

    project->values("QMAKE_L_FLAG") << "-L";

    processVars();

    if (!project->values("RES_FILE").isEmpty()) {
        project->values("QMAKE_LIBS") += escapeFilePaths(project->values("RES_FILE"));
    }

    ProStringList &configs = project->values("CONFIG");

    if(project->isActiveConfig("qt_dll"))
        if(configs.indexOf("qt") == -1)
            configs.append("qt");

    if (project->isActiveConfig("dll")) {
        QString destDir = "";
        if(!project->first("DESTDIR").isEmpty())
            destDir = Option::fixPathToTargetOS(project->first("DESTDIR") + Option::dir_sep, false, false);
        project->values("MINGW_IMPORT_LIB").prepend(destDir + "lib" + project->first("TARGET")
                                                         + project->first("TARGET_VERSION_EXT") + ".a");
	project->values("QMAKE_LFLAGS").append(QString("-Wl,--out-implib,") + project->first("MINGW_IMPORT_LIB"));
    }

    if (!project->values("DEF_FILE").isEmpty()) {
        QString defFileName = fileFixify(project->first("DEF_FILE").toQString());
        project->values("QMAKE_LFLAGS").append(QString("-Wl,") + escapeFilePath(defFileName));
    }

    if (project->isActiveConfig("staticlib") && project->first("TEMPLATE") == "lib")
        project->values("QMAKE_LFLAGS").append("-static");

    MakefileGenerator::init();

    // precomp
    if (!project->first("PRECOMPILED_HEADER").isEmpty()
        && project->isActiveConfig("precompile_header")) {
        QString preCompHeader = var("PRECOMPILED_DIR")
                    + QFileInfo(project->first("PRECOMPILED_HEADER").toQString()).fileName();
	preCompHeaderOut = preCompHeader + ".gch";
	project->values("QMAKE_CLEAN").append(preCompHeaderOut + Option::dir_sep + "c");
	project->values("QMAKE_CLEAN").append(preCompHeaderOut + Option::dir_sep + "c++");

	project->values("QMAKE_RUN_CC").clear();
	project->values("QMAKE_RUN_CC").append("$(CC) -c -include " + preCompHeader +
                                                    " $(CFLAGS) $(INCPATH) -o $obj $src");
        project->values("QMAKE_RUN_CC_IMP").clear();
	project->values("QMAKE_RUN_CC_IMP").append("$(CC)  -c -include " + preCompHeader +
                                                        " $(CFLAGS) $(INCPATH) -o $@ $<");
        project->values("QMAKE_RUN_CXX").clear();
	project->values("QMAKE_RUN_CXX").append("$(CXX) -c -include " + preCompHeader +
                                                     " $(CXXFLAGS) $(INCPATH) -o $obj $src");
        project->values("QMAKE_RUN_CXX_IMP").clear();
	project->values("QMAKE_RUN_CXX_IMP").append("$(CXX) -c -include " + preCompHeader +
                                                         " $(CXXFLAGS) $(INCPATH) -o $@ $<");
    }

    if(project->isActiveConfig("dll")) {
        project->values("QMAKE_CLEAN").append(project->first("MINGW_IMPORT_LIB"));
    }
}
Пример #8
0
void Win32MakefileGenerator::processVars()
{
    project->values("QMAKE_ORIG_TARGET") = project->values("TARGET");
    if (project->isEmpty("QMAKE_PROJECT_NAME"))
        project->values("QMAKE_PROJECT_NAME") = project->values("QMAKE_ORIG_TARGET");
    else if (project->first("TEMPLATE").startsWith("vc"))
        project->values("MAKEFILE") = project->values("QMAKE_PROJECT_NAME");

    if (!project->values("QMAKE_INCDIR").isEmpty())
        project->values("INCLUDEPATH") += project->values("QMAKE_INCDIR");

    if (!project->values("VERSION").isEmpty()) {
        QStringList l = project->first("VERSION").toQString().split('.');
        if (l.size() > 0)
            project->values("VER_MAJ").append(l[0]);
        if (l.size() > 1)
            project->values("VER_MIN").append(l[1]);
    }

    // TARGET_VERSION_EXT will be used to add a version number onto the target name
    if (!project->isActiveConfig("skip_target_version_ext")
            && project->values("TARGET_VERSION_EXT").isEmpty()
            && !project->values("VER_MAJ").isEmpty())
        project->values("TARGET_VERSION_EXT").append(project->values("VER_MAJ").first());

    if(project->isEmpty("QMAKE_COPY_FILE"))
        project->values("QMAKE_COPY_FILE").append("$(COPY)");
    if(project->isEmpty("QMAKE_COPY_DIR"))
        project->values("QMAKE_COPY_DIR").append("xcopy /s /q /y /i");
    if (project->isEmpty("QMAKE_STREAM_EDITOR"))
        project->values("QMAKE_STREAM_EDITOR").append("$(QMAKE) -install sed");
    if(project->isEmpty("QMAKE_INSTALL_FILE"))
        project->values("QMAKE_INSTALL_FILE").append("$(COPY_FILE)");
    if(project->isEmpty("QMAKE_INSTALL_PROGRAM"))
        project->values("QMAKE_INSTALL_PROGRAM").append("$(COPY_FILE)");
    if(project->isEmpty("QMAKE_INSTALL_DIR"))
        project->values("QMAKE_INSTALL_DIR").append("$(COPY_DIR)");

    fixTargetExt();
    processRcFileVar();

    ProStringList &incDir = project->values("INCLUDEPATH");
    for (ProStringList::Iterator incDir_it = incDir.begin(); incDir_it != incDir.end(); ++incDir_it)
        if (!(*incDir_it).isEmpty())
            (*incDir_it) = Option::fixPathToTargetOS((*incDir_it).toQString(), false, false);

    ProString libArg = project->first("QMAKE_L_FLAG");
    ProStringList libs;
    ProStringList &libDir = project->values("QMAKE_LIBDIR");
    for (ProStringList::Iterator libDir_it = libDir.begin(); libDir_it != libDir.end(); ++libDir_it) {
        QString lib = (*libDir_it).toQString();
        if (!lib.isEmpty()) {
            lib.remove('"');
            if (lib.endsWith('\\'))
                lib.chop(1);
            libs << libArg + escapeFilePath(Option::fixPathToTargetOS(lib, false, false));
        }
    }
    project->values("QMAKE_LIBS") += libs + escapeFilePaths(project->values("LIBS"));
    project->values("QMAKE_LIBS_PRIVATE") += escapeFilePaths(project->values("LIBS_PRIVATE"));

    if (project->values("TEMPLATE").contains("app")) {
        project->values("QMAKE_CFLAGS") += project->values("QMAKE_CFLAGS_APP");
        project->values("QMAKE_CXXFLAGS") += project->values("QMAKE_CXXFLAGS_APP");
        project->values("QMAKE_LFLAGS") += project->values("QMAKE_LFLAGS_APP");
    } else if (project->values("TEMPLATE").contains("lib") && project->isActiveConfig("dll")) {
        if(!project->isActiveConfig("plugin") || !project->isActiveConfig("plugin_no_share_shlib_cflags")) {
            project->values("QMAKE_CFLAGS") += project->values("QMAKE_CFLAGS_SHLIB");
            project->values("QMAKE_CXXFLAGS") += project->values("QMAKE_CXXFLAGS_SHLIB");
        }
        if (project->isActiveConfig("plugin")) {
            project->values("QMAKE_CFLAGS") += project->values("QMAKE_CFLAGS_PLUGIN");
            project->values("QMAKE_CXXFLAGS") += project->values("QMAKE_CXXFLAGS_PLUGIN");
            project->values("QMAKE_LFLAGS") += project->values("QMAKE_LFLAGS_PLUGIN");
        } else {
            project->values("QMAKE_LFLAGS") += project->values("QMAKE_LFLAGS_SHLIB");
        }
    }
}
Пример #9
0
QT_BEGIN_NAMESPACE

void
UnixMakefileGenerator::init()
{
    if(init_flag)
        return;
    init_flag = true;

    if(project->isEmpty("QMAKE_EXTENSION_SHLIB")) {
        if(project->isEmpty("QMAKE_CYGWIN_SHLIB")) {
            project->values("QMAKE_EXTENSION_SHLIB").append("so");
        } else {
            project->values("QMAKE_EXTENSION_SHLIB").append("dll");
        }
    }

    if (project->isEmpty("QMAKE_PREFIX_SHLIB"))
        // Prevent crash when using the empty variable.
        project->values("QMAKE_PREFIX_SHLIB").append("");

    if(!project->isEmpty("QMAKE_FAILED_REQUIREMENTS")) /* no point */
        return;

    QStringList &configs = project->values("CONFIG");
    if(project->isEmpty("ICON") && !project->isEmpty("RC_FILE"))
        project->values("ICON") = project->values("RC_FILE");
    if(project->isEmpty("QMAKE_EXTENSION_PLUGIN"))
        project->values("QMAKE_EXTENSION_PLUGIN").append(project->first("QMAKE_EXTENSION_SHLIB"));
    if(project->isEmpty("QMAKE_COPY_FILE"))
        project->values("QMAKE_COPY_FILE").append("$(COPY)");
    if(project->isEmpty("QMAKE_STREAM_EDITOR"))
        project->values("QMAKE_STREAM_EDITOR").append("sed");
    if(project->isEmpty("QMAKE_COPY_DIR"))
        project->values("QMAKE_COPY_DIR").append("$(COPY) -R");
    if(project->isEmpty("QMAKE_INSTALL_FILE"))
        project->values("QMAKE_INSTALL_FILE").append("$(COPY_FILE)");
    if(project->isEmpty("QMAKE_INSTALL_DIR"))
        project->values("QMAKE_INSTALL_DIR").append("$(COPY_DIR)");
    if(project->isEmpty("QMAKE_INSTALL_PROGRAM"))
        project->values("QMAKE_INSTALL_PROGRAM").append("$(COPY_FILE)");
    if(project->isEmpty("QMAKE_LIBTOOL"))
        project->values("QMAKE_LIBTOOL").append("libtool --silent");
    if(project->isEmpty("QMAKE_SYMBOLIC_LINK"))
        project->values("QMAKE_SYMBOLIC_LINK").append("ln -f -s");

    /* this should probably not be here, but I'm using it to wrap the .t files */
    if(project->first("TEMPLATE") == "app")
        project->values("QMAKE_APP_FLAG").append("1");
    else if(project->first("TEMPLATE") == "lib")
        project->values("QMAKE_LIB_FLAG").append("1");
    else if(project->first("TEMPLATE") == "subdirs") {
        MakefileGenerator::init();
        if(project->isEmpty("MAKEFILE"))
            project->values("MAKEFILE").append("Makefile");
        if(project->values("QMAKE_INTERNAL_QMAKE_DEPS").indexOf("qmake_all") == -1)
            project->values("QMAKE_INTERNAL_QMAKE_DEPS").append("qmake_all");
        return; /* subdirs is done */
    }

    //If the TARGET looks like a path split it into DESTDIR and the resulting TARGET
    if(!project->isEmpty("TARGET")) {
        project->values("TARGET") = escapeFilePaths(project->values("TARGET"));
        QString targ = unescapeFilePath(project->first("TARGET"));
        int slsh = qMax(targ.lastIndexOf('/'), targ.lastIndexOf(Option::dir_sep));
        if(slsh != -1) {
            if(project->isEmpty("DESTDIR"))
                project->values("DESTDIR").append("");
            else if(project->first("DESTDIR").right(1) != Option::dir_sep)
                project->values("DESTDIR") = QStringList(project->first("DESTDIR") + Option::dir_sep);
            project->values("DESTDIR") = QStringList(project->first("DESTDIR") + targ.left(slsh+1));
            project->values("TARGET") = QStringList(targ.mid(slsh+1));
        }
    }

    project->values("QMAKE_ORIG_TARGET") = project->values("TARGET");
    project->values("QMAKE_ORIG_DESTDIR") = project->values("DESTDIR");
    project->values("QMAKE_LIBS") += escapeFilePaths(project->values("LIBS"));
    project->values("QMAKE_LIBS_PRIVATE") += escapeFilePaths(project->values("LIBS_PRIVATE"));
    if((!project->isEmpty("QMAKE_LIB_FLAG") && !project->isActiveConfig("staticlib")) ||
       (project->isActiveConfig("qt") &&  project->isActiveConfig("plugin"))) {
        if(configs.indexOf("dll") == -1) configs.append("dll");
    } else if(!project->isEmpty("QMAKE_APP_FLAG") || project->isActiveConfig("dll")) {
        configs.removeAll("staticlib");
    }
    if(!project->isEmpty("QMAKE_INCREMENTAL"))
        project->values("QMAKE_LFLAGS") += project->values("QMAKE_LFLAGS_INCREMENTAL");
    else if(!project->isEmpty("QMAKE_LFLAGS_PREBIND") &&
            !project->values("QMAKE_LIB_FLAG").isEmpty() &&
            project->isActiveConfig("dll"))
        project->values("QMAKE_LFLAGS") += project->values("QMAKE_LFLAGS_PREBIND");
    if(!project->isEmpty("QMAKE_INCDIR"))
        project->values("INCLUDEPATH") += project->values("QMAKE_INCDIR");
    if(!project->isEmpty("QMAKE_LIBDIR")) {
        const QStringList &libdirs = project->values("QMAKE_LIBDIR");
        for(int i = 0; i < libdirs.size(); ++i) {
            if(!project->isEmpty("QMAKE_LFLAGS_RPATH") && project->isActiveConfig("rpath_libdirs"))
                project->values("QMAKE_LFLAGS") += var("QMAKE_LFLAGS_RPATH") + libdirs[i];
            if (project->isActiveConfig("rvct_linker")) {
                project->values("QMAKE_LIBDIR_FLAGS") += "--userlibpath " + escapeFilePath(libdirs[i]);
            } else {
                project->values("QMAKE_LIBDIR_FLAGS") += "-L" + escapeFilePath(libdirs[i]);
            }
        }
    }
    if(project->isActiveConfig("macx") && !project->isEmpty("QMAKE_FRAMEWORKPATH")) {
        const QStringList &fwdirs = project->values("QMAKE_FRAMEWORKPATH");
        for(int i = 0; i < fwdirs.size(); ++i) {
            project->values("QMAKE_FRAMEWORKPATH_FLAGS") += "-F" + escapeFilePath(fwdirs[i]);
        }
    }
    if(!project->isEmpty("QMAKE_RPATHDIR")) {
        const QStringList &rpathdirs = project->values("QMAKE_RPATHDIR");
        for(int i = 0; i < rpathdirs.size(); ++i) {
            if(!project->isEmpty("QMAKE_LFLAGS_RPATH"))
                project->values("QMAKE_LFLAGS") += var("QMAKE_LFLAGS_RPATH") + escapeFilePath(QFileInfo(rpathdirs[i]).absoluteFilePath());
        }
    }

    project->values("QMAKE_FILETAGS") << "SOURCES" << "GENERATED_SOURCES" << "TARGET" << "DESTDIR";
    if(!project->isEmpty("QMAKE_EXTRA_COMPILERS")) {
        const QStringList &quc = project->values("QMAKE_EXTRA_COMPILERS");
        for(int i = 0; i < quc.size(); ++i)
            project->values("QMAKE_FILETAGS") += project->values(quc[i]+".input");
    }

    if(project->isActiveConfig("GNUmake") && !project->isEmpty("QMAKE_CFLAGS_DEPS"))
        include_deps = true; //do not generate deps
    if(project->isActiveConfig("compile_libtool"))
        Option::obj_ext = ".lo"; //override the .o

    MakefileGenerator::init();

    QString comps[] = { "C", "CXX", "OBJC", "OBJCXX", QString() };
    for(int i = 0; !comps[i].isNull(); i++) {
        QString compile_flag = var("QMAKE_COMPILE_FLAG");
        if(compile_flag.isEmpty())
            compile_flag = "-c";

        if(doPrecompiledHeaders() && !project->isEmpty("PRECOMPILED_HEADER")) {
            QString pchFlags = var("QMAKE_" + comps[i] + "FLAGS_USE_PRECOMPILE");

            QString pchBaseName;
            if(!project->isEmpty("PRECOMPILED_DIR")) {
                pchBaseName = Option::fixPathToTargetOS(project->first("PRECOMPILED_DIR"));
                if(!pchBaseName.endsWith(Option::dir_sep))
                    pchBaseName += Option::dir_sep;
            }
            pchBaseName += project->first("QMAKE_ORIG_TARGET");

            // replace place holders
            pchFlags = pchFlags.replace("${QMAKE_PCH_INPUT}",
                                        fileFixify(project->first("PRECOMPILED_HEADER")));
            pchFlags = pchFlags.replace("${QMAKE_PCH_OUTPUT_BASE}", pchBaseName);
            if (project->isActiveConfig("icc_pch_style")) {
                // icc style
                pchFlags = pchFlags.replace("${QMAKE_PCH_OUTPUT}",
                                            pchBaseName + project->first("QMAKE_PCH_OUTPUT_EXT"));
            }

            if (!pchFlags.isEmpty())
                compile_flag += " " + pchFlags;
        }

        QString cflags;
        if(comps[i] == "OBJC" || comps[i] == "OBJCXX")
            cflags += " $(CFLAGS)";
        else
            cflags += " $(" + comps[i] + "FLAGS)";
        compile_flag += cflags + " $(INCPATH)";

        QString compiler = comps[i];
        if (compiler == "C")
            compiler = "CC";

        QString runComp = "QMAKE_RUN_" + compiler;
        if(project->isEmpty(runComp))
            project->values(runComp).append("$(" + compiler + ") " + compile_flag + " -o $obj $src");
        QString runCompImp = "QMAKE_RUN_" + compiler + "_IMP";
        if(project->isEmpty(runCompImp))
            project->values(runCompImp).append("$(" + compiler + ") " + compile_flag + " -o \"$@\" \"$<\"");
    }

    if(project->isActiveConfig("macx") && !project->isEmpty("TARGET") && !project->isActiveConfig("compile_libtool") &&
       ((project->isActiveConfig("build_pass") || project->isEmpty("BUILDS")))) {
        QString bundle;
        if(project->isActiveConfig("bundle") && !project->isEmpty("QMAKE_BUNDLE_EXTENSION")) {
            bundle = unescapeFilePath(project->first("TARGET"));
            if(!project->isEmpty("QMAKE_BUNDLE_NAME"))
                bundle = unescapeFilePath(project->first("QMAKE_BUNDLE_NAME"));
            if(!bundle.endsWith(project->first("QMAKE_BUNDLE_EXTENSION")))
                bundle += project->first("QMAKE_BUNDLE_EXTENSION");
        } else if(project->first("TEMPLATE") == "app" && project->isActiveConfig("app_bundle")) {
            bundle = unescapeFilePath(project->first("TARGET"));
            if(!project->isEmpty("QMAKE_APPLICATION_BUNDLE_NAME"))
                bundle = unescapeFilePath(project->first("QMAKE_APPLICATION_BUNDLE_NAME"));
            if(!bundle.endsWith(".app"))
                bundle += ".app";
            if(project->isEmpty("QMAKE_BUNDLE_LOCATION"))
                project->values("QMAKE_BUNDLE_LOCATION").append("Contents/MacOS");
            project->values("QMAKE_PKGINFO").append(project->first("DESTDIR") + bundle + "/Contents/PkgInfo");
            project->values("QMAKE_BUNDLE_RESOURCE_FILE").append(project->first("DESTDIR") + bundle + "/Contents/Resources/empty.lproj");
        } else if(project->first("TEMPLATE") == "lib" && !project->isActiveConfig("staticlib") &&
                  ((!project->isActiveConfig("plugin") && project->isActiveConfig("lib_bundle")) ||
                   (project->isActiveConfig("plugin") && project->isActiveConfig("plugin_bundle")))) {
            bundle = unescapeFilePath(project->first("TARGET"));
            if(project->isActiveConfig("plugin")) {
                if(!project->isEmpty("QMAKE_PLUGIN_BUNDLE_NAME"))
                    bundle = unescapeFilePath(project->first("QMAKE_PLUGIN_BUNDLE_NAME"));
                if(!project->isEmpty("QMAKE_BUNDLE_EXTENSION") && !bundle.endsWith(project->first("QMAKE_BUNDLE_EXTENSION")))
                    bundle += project->first("QMAKE_BUNDLE_EXTENSION");
                else if(!bundle.endsWith(".plugin"))
                    bundle += ".plugin";
                if(project->isEmpty("QMAKE_BUNDLE_LOCATION"))
                    project->values("QMAKE_BUNDLE_LOCATION").append("Contents/MacOS");
            } else {
                if(!project->isEmpty("QMAKE_FRAMEWORK_BUNDLE_NAME"))
                    bundle = unescapeFilePath(project->first("QMAKE_FRAMEWORK_BUNDLE_NAME"));
                if(!project->isEmpty("QMAKE_BUNDLE_EXTENSION") && !bundle.endsWith(project->first("QMAKE_BUNDLE_EXTENSION")))
                    bundle += project->first("QMAKE_BUNDLE_EXTENSION");
                else if(!bundle.endsWith(".framework"))
                    bundle += ".framework";
            }
        }
        if(!bundle.isEmpty()) {
            project->values("QMAKE_BUNDLE") = QStringList(bundle);
            project->values("ALL_DEPS") += project->first("QMAKE_PKGINFO");
            project->values("ALL_DEPS") += project->first("QMAKE_BUNDLE_RESOURCE_FILE");
        } else {
            project->values("QMAKE_BUNDLE").clear();
            project->values("QMAKE_BUNDLE_LOCATION").clear();
        }
    } else { //no bundling here
        project->values("QMAKE_BUNDLE").clear();
        project->values("QMAKE_BUNDLE_LOCATION").clear();
    }

    if(!project->isEmpty("QMAKE_INTERNAL_INCLUDED_FILES"))
        project->values("DISTFILES") += project->values("QMAKE_INTERNAL_INCLUDED_FILES");
    project->values("DISTFILES") += project->projectFile();

    init2();
    project->values("QMAKE_INTERNAL_PRL_LIBS") << "QMAKE_LIBDIR_FLAGS" << "QMAKE_FRAMEWORKPATH_FLAGS" << "QMAKE_LIBS";
    if(!project->isEmpty("QMAKE_MAX_FILES_PER_AR")) {
        bool ok;
        int max_files = project->first("QMAKE_MAX_FILES_PER_AR").toInt(&ok);
        QStringList ar_sublibs, objs = project->values("OBJECTS");
        if(ok && max_files > 5 && max_files < (int)objs.count()) {
            QString lib;
            for(int i = 0, obj_cnt = 0, lib_cnt = 0; i != objs.size(); ++i) {
                if((++obj_cnt) >= max_files) {
                    if(lib_cnt) {
                        lib.sprintf("lib%s-tmp%d.a",
                                    project->first("QMAKE_ORIG_TARGET").toLatin1().constData(), lib_cnt);
                        ar_sublibs << lib;
                        obj_cnt = 0;
                    }
                    lib_cnt++;
                }
            }
        }
        if(!ar_sublibs.isEmpty()) {
            project->values("QMAKE_AR_SUBLIBS") = ar_sublibs;
            project->values("QMAKE_INTERNAL_PRL_LIBS") << "QMAKE_AR_SUBLIBS";
        }
    }

    if(project->isActiveConfig("compile_libtool")) {
        const QString libtoolify[] = { "QMAKE_RUN_CC", "QMAKE_RUN_CC_IMP",
                                       "QMAKE_RUN_CXX", "QMAKE_RUN_CXX_IMP",
                                       "QMAKE_LINK_THREAD", "QMAKE_LINK", "QMAKE_AR_CMD", "QMAKE_LINK_SHLIB_CMD",
                                       QString() };
        for(int i = 0; !libtoolify[i].isNull(); i++) {
            QStringList &l = project->values(libtoolify[i]);
            if(!l.isEmpty()) {
                QString libtool_flags, comp_flags;
                if(libtoolify[i].startsWith("QMAKE_LINK") || libtoolify[i] == "QMAKE_AR_CMD") {
                    libtool_flags += " --mode=link";
                    if(project->isActiveConfig("staticlib")) {
                        libtool_flags += " -static";
                    } else {
                        if(!project->isEmpty("QMAKE_LIB_FLAG")) {
                            int maj = project->first("VER_MAJ").toInt();
                            int min = project->first("VER_MIN").toInt();
                            int pat = project->first("VER_PAT").toInt();
                            comp_flags += " -version-info " + QString::number(10*maj + min) +
                                          ":" + QString::number(pat) + ":0";
                            if(libtoolify[i] != "QMAKE_AR_CMD") {
                                QString rpath = Option::output_dir;
                                if(!project->isEmpty("DESTDIR")) {
                                    rpath = project->first("DESTDIR");
                                    if(QDir::isRelativePath(rpath))
                                        rpath.prepend(Option::output_dir + Option::dir_sep);
                                }
                                comp_flags += " -rpath " + Option::fixPathToTargetOS(rpath, false);
                            }
                        }
                    }
                    if(project->isActiveConfig("plugin"))
                        libtool_flags += " -module";
                } else {
                    libtool_flags += " --mode=compile";
                }
                l.first().prepend("$(LIBTOOL)" + libtool_flags + " ");
                if(!comp_flags.isEmpty())
                    l.first() += comp_flags;
            }
        }
    }
}
Пример #10
0
void NmakeMakefileGenerator::init()
{
    if(init_flag)
        return;
    init_flag = true;

    /* this should probably not be here, but I'm using it to wrap the .t files */
    if(project->first("TEMPLATE") == "app")
        project->values("QMAKE_APP_FLAG").append("1");
    else if(project->first("TEMPLATE") == "lib")
        project->values("QMAKE_LIB_FLAG").append("1");
    else if(project->first("TEMPLATE") == "subdirs") {
        MakefileGenerator::init();
        if(project->values("MAKEFILE").isEmpty())
            project->values("MAKEFILE").append("Makefile");
        if(project->isEmpty("QMAKE_COPY_FILE"))
            project->values("QMAKE_COPY_FILE").append("$(COPY)");
        if(project->isEmpty("QMAKE_COPY_DIR"))
            project->values("QMAKE_COPY_DIR").append("xcopy /s /q /y /i");
        if(project->isEmpty("QMAKE_INSTALL_FILE"))
            project->values("QMAKE_INSTALL_FILE").append("$(COPY_FILE)");
        if(project->isEmpty("QMAKE_INSTALL_PROGRAM"))
            project->values("QMAKE_INSTALL_PROGRAM").append("$(COPY_FILE)");
        if(project->isEmpty("QMAKE_INSTALL_DIR"))
            project->values("QMAKE_INSTALL_DIR").append("$(COPY_DIR)");
        return;
    }

    project->values("QMAKE_LIBS") += escapeFilePaths(project->values("LIBS"));
    project->values("QMAKE_LIBS_PRIVATE") += escapeFilePaths(project->values("LIBS_PRIVATE"));
    processVars();

    if (!project->values("RES_FILE").isEmpty()) {
        project->values("QMAKE_LIBS") += escapeFilePaths(project->values("RES_FILE"));
    }

    if (!project->values("DEF_FILE").isEmpty()) {
        QString defFileName = fileFixify(project->values("DEF_FILE")).first();
        project->values("QMAKE_LFLAGS").append(QString("/DEF:") + escapeFilePath(defFileName));
    }

    if(!project->values("VERSION").isEmpty()) {
        QString version = project->values("VERSION")[0];
        int firstDot = version.indexOf(".");
        QString major = version.left(firstDot);
        QString minor = version.right(version.length() - firstDot - 1);
        minor.replace(".", "");
        project->values("QMAKE_LFLAGS").append("/VERSION:" + major + "." + minor);
    }

    // Base class init!
    MakefileGenerator::init();

    // Setup PCH variables
    precompH = project->first("PRECOMPILED_HEADER");
    usePCH = !precompH.isEmpty() && project->isActiveConfig("precompile_header");
    if (usePCH) {
        // Created files
        precompObj = var("PRECOMPILED_DIR") + project->first("TARGET") + "_pch" + Option::obj_ext;
        precompPch = var("PRECOMPILED_DIR") + project->first("TARGET") + "_pch.pch";
        // Add linking of precompObj (required for whole precompiled classes)
        project->values("OBJECTS")                  += precompObj;
        // Add pch file to cleanup
        project->values("QMAKE_CLEAN")          += precompPch;
        // Return to variable pool
        project->values("PRECOMPILED_OBJECT") = QStringList(precompObj);
        project->values("PRECOMPILED_PCH")    = QStringList(precompPch);
    }

    QString version = project->first("TARGET_VERSION_EXT");
    if(project->isActiveConfig("shared")) {
        project->values("QMAKE_CLEAN").append(project->first("DESTDIR") + project->first("TARGET") + version + ".exp");
    }
    if(project->isActiveConfig("debug")) {
        project->values("QMAKE_DISTCLEAN").append(project->first("DESTDIR") + project->first("TARGET") + version + ".pdb");
        project->values("QMAKE_CLEAN").append(project->first("DESTDIR") + project->first("TARGET") + version + ".ilk");
        project->values("QMAKE_CLEAN").append("vc*.pdb");
        project->values("QMAKE_CLEAN").append("vc*.idb");
    }
}
Пример #11
0
QT_BEGIN_NAMESPACE

void
UnixMakefileGenerator::init()
{
    ProStringList &configs = project->values("CONFIG");
    if(project->isEmpty("ICON") && !project->isEmpty("RC_FILE"))
        project->values("ICON") = project->values("RC_FILE");
    if(project->isEmpty("QMAKE_EXTENSION_PLUGIN"))
        project->values("QMAKE_EXTENSION_PLUGIN").append(project->first("QMAKE_EXTENSION_SHLIB"));

    project->values("QMAKE_ORIG_TARGET") = project->values("TARGET");

    //version handling
    if (project->isEmpty("VERSION")) {
        project->values("VERSION").append(
            "1.0." + (project->isEmpty("VER_PAT") ? QString("0") : project->first("VER_PAT")));
    }
    QStringList l = project->first("VERSION").toQString().split('.');
    l << "0" << "0"; //make sure there are three
    project->values("VER_MAJ").append(l[0]);
    project->values("VER_MIN").append(l[1]);
    project->values("VER_PAT").append(l[2]);

    QString sroot = project->sourceRoot();
    foreach (const ProString &iif, project->values("QMAKE_INTERNAL_INCLUDED_FILES")) {
        if (iif == project->cacheFile())
            continue;
        if (iif.startsWith(sroot) && iif.at(sroot.length()) == QLatin1Char('/'))
            project->values("DISTFILES") += fileFixify(iif.toQString(), FileFixifyRelative);
    }

    /* this should probably not be here, but I'm using it to wrap the .t files */
    if(project->first("TEMPLATE") == "app")
        project->values("QMAKE_APP_FLAG").append("1");
    else if(project->first("TEMPLATE") == "lib")
        project->values("QMAKE_LIB_FLAG").append("1");
    else if(project->first("TEMPLATE") == "subdirs") {
        MakefileGenerator::init();
        if(project->isEmpty("MAKEFILE"))
            project->values("MAKEFILE").append("Makefile");
        return; /* subdirs is done */
    }

    project->values("QMAKE_ORIG_DESTDIR") = project->values("DESTDIR");
    project->values("QMAKE_LIBS") += project->values("LIBS");
    project->values("QMAKE_LIBS_PRIVATE") += project->values("LIBS_PRIVATE");
    if((!project->isEmpty("QMAKE_LIB_FLAG") && !project->isActiveConfig("staticlib")) ||
       (project->isActiveConfig("qt") &&  project->isActiveConfig("plugin"))) {
        if(configs.indexOf("dll") == -1) configs.append("dll");
    } else if(!project->isEmpty("QMAKE_APP_FLAG") || project->isActiveConfig("dll")) {
        configs.removeAll("staticlib");
    }
    if(!project->isEmpty("QMAKE_INCREMENTAL"))
        project->values("QMAKE_LFLAGS") += project->values("QMAKE_LFLAGS_INCREMENTAL");
    else if(!project->isEmpty("QMAKE_LFLAGS_PREBIND") &&
            !project->values("QMAKE_LIB_FLAG").isEmpty() &&
            project->isActiveConfig("dll"))
        project->values("QMAKE_LFLAGS") += project->values("QMAKE_LFLAGS_PREBIND");
    if(!project->isEmpty("QMAKE_INCDIR"))
        project->values("INCLUDEPATH") += project->values("QMAKE_INCDIR");
    ProStringList ldadd;
    if(!project->isEmpty("QMAKE_LIBDIR")) {
        const ProStringList &libdirs = project->values("QMAKE_LIBDIR");
        for(int i = 0; i < libdirs.size(); ++i) {
            if(!project->isEmpty("QMAKE_LFLAGS_RPATH") && project->isActiveConfig("rpath_libdirs"))
                project->values("QMAKE_LFLAGS") += var("QMAKE_LFLAGS_RPATH") + libdirs[i];
            project->values("QMAKE_LIBDIR_FLAGS") += "-L" + escapeFilePath(libdirs[i]);
        }
    }
    ldadd += project->values("QMAKE_LIBDIR_FLAGS");
    if (project->isActiveConfig("mac")) {
        if (!project->isEmpty("QMAKE_FRAMEWORKPATH")) {
            const ProStringList &fwdirs = project->values("QMAKE_FRAMEWORKPATH");
            for (int i = 0; i < fwdirs.size(); ++i)
                project->values("QMAKE_FRAMEWORKPATH_FLAGS") += "-F" + escapeFilePath(fwdirs[i]);
        }
        ldadd += project->values("QMAKE_FRAMEWORKPATH_FLAGS");
    }
    ProStringList &qmklibs = project->values("QMAKE_LIBS");
    qmklibs = ldadd + qmklibs;
    if (!project->isEmpty("QMAKE_RPATHDIR") && !project->isEmpty("QMAKE_LFLAGS_RPATH")) {
        const ProStringList &rpathdirs = project->values("QMAKE_RPATHDIR");
        for (int i = 0; i < rpathdirs.size(); ++i) {
            QString rpathdir = rpathdirs[i].toQString();
            if (rpathdir.length() > 1 && rpathdir.at(0) == '$' && rpathdir.at(1) != '(') {
                rpathdir.replace(0, 1, "\\$$");  // Escape from make and the shell
            } else if (!rpathdir.startsWith('@') && fileInfo(rpathdir).isRelative()) {
                QString rpathbase = project->first("QMAKE_REL_RPATH_BASE").toQString();
                if (rpathbase.isEmpty()) {
                    fprintf(stderr, "Error: This platform does not support relative paths in QMAKE_RPATHDIR (%s)\n",
                                    rpathdir.toLatin1().constData());
                    continue;
                }
                if (rpathbase.startsWith('$'))
                    rpathbase.replace(0, 1, "\\$$");  // Escape from make and the shell
                if (rpathdir == ".")
                    rpathdir = rpathbase;
                else
                    rpathdir.prepend(rpathbase + '/');
                project->values("QMAKE_LFLAGS").insertUnique(project->values("QMAKE_LFLAGS_REL_RPATH"));
            }
            project->values("QMAKE_LFLAGS") += var("QMAKE_LFLAGS_RPATH") + escapeFilePath(rpathdir);
        }
    }
    if (!project->isEmpty("QMAKE_RPATHLINKDIR")) {
        const ProStringList &rpathdirs = project->values("QMAKE_RPATHLINKDIR");
        for (int i = 0; i < rpathdirs.size(); ++i) {
            if (!project->isEmpty("QMAKE_LFLAGS_RPATHLINK"))
                project->values("QMAKE_LFLAGS") += var("QMAKE_LFLAGS_RPATHLINK") + escapeFilePath(QFileInfo(rpathdirs[i].toQString()).absoluteFilePath());
        }
    }

    if(project->isActiveConfig("GNUmake") && !project->isEmpty("QMAKE_CFLAGS_DEPS"))
        include_deps = true; //do not generate deps

    MakefileGenerator::init();

    if (project->isActiveConfig("objective_c"))
        project->values("QMAKE_BUILTIN_COMPILERS") << "OBJC" << "OBJCXX";

    foreach (const ProString &compiler, project->values("QMAKE_BUILTIN_COMPILERS")) {
        QString compile_flag = var("QMAKE_COMPILE_FLAG");
        if(compile_flag.isEmpty())
            compile_flag = "-c";

        if(doPrecompiledHeaders() && !project->isEmpty("PRECOMPILED_HEADER")) {
            QString pchFlags = var(ProKey("QMAKE_" + compiler + "FLAGS_USE_PRECOMPILE"));

            QString pchBaseName;
            if(!project->isEmpty("PRECOMPILED_DIR")) {
                pchBaseName = Option::fixPathToTargetOS(project->first("PRECOMPILED_DIR").toQString());
                if(!pchBaseName.endsWith(Option::dir_sep))
                    pchBaseName += Option::dir_sep;
            }
            pchBaseName += project->first("QMAKE_ORIG_TARGET").toQString();

            // replace place holders
            pchFlags.replace(QLatin1String("${QMAKE_PCH_INPUT}"),
                             escapeFilePath(project->first("PRECOMPILED_HEADER").toQString()));
            pchFlags.replace(QLatin1String("${QMAKE_PCH_OUTPUT_BASE}"), escapeFilePath(pchBaseName));
            if (project->isActiveConfig("icc_pch_style")) {
                // icc style
                pchFlags.replace(QLatin1String("${QMAKE_PCH_OUTPUT}"),
                                 escapeFilePath(pchBaseName + project->first("QMAKE_PCH_OUTPUT_EXT")));
            } else {
                // gcc style (including clang_pch_style)
                QString headerSuffix;
                if (project->isActiveConfig("clang_pch_style"))
                    headerSuffix = project->first("QMAKE_PCH_OUTPUT_EXT").toQString();
                else
                    pchBaseName += project->first("QMAKE_PCH_OUTPUT_EXT").toQString();

                pchBaseName += Option::dir_sep;

                ProString language = project->first(ProKey("QMAKE_LANGUAGE_" + compiler));
                if (!language.isEmpty()) {
                    pchFlags.replace(QLatin1String("${QMAKE_PCH_OUTPUT}"),
                                     escapeFilePath(pchBaseName + language + headerSuffix));
                }
            }

            if (!pchFlags.isEmpty())
                compile_flag += " " + pchFlags;
        }

        QString compilerExecutable;
        if (compiler == "C" || compiler == "OBJC") {
            compilerExecutable = "$(CC)";
            compile_flag += " $(CFLAGS)";
        } else {
            compilerExecutable = "$(CXX)";
            compile_flag += " $(CXXFLAGS)";
        }

        compile_flag += " $(INCPATH)";

        ProString compilerVariable = compiler;
        if (compilerVariable == "C")
            compilerVariable = ProString("CC");

        const ProKey runComp("QMAKE_RUN_" + compilerVariable);
        if(project->isEmpty(runComp))
            project->values(runComp).append(compilerExecutable + " " + compile_flag + " " + var("QMAKE_CC_O_FLAG") + "$obj $src");
        const ProKey runCompImp("QMAKE_RUN_" + compilerVariable + "_IMP");
        if(project->isEmpty(runCompImp))
            project->values(runCompImp).append(compilerExecutable + " " + compile_flag + " " + var("QMAKE_CC_O_FLAG") + "\"$@\" \"$<\"");
    }

    if (project->isActiveConfig("mac") && !project->isEmpty("TARGET") &&
       ((project->isActiveConfig("build_pass") || project->isEmpty("BUILDS")))) {
        ProString bundle;
        if(project->isActiveConfig("bundle") && !project->isEmpty("QMAKE_BUNDLE_EXTENSION")) {
            bundle = project->first("TARGET");
            if(!project->isEmpty("QMAKE_BUNDLE_NAME"))
                bundle = project->first("QMAKE_BUNDLE_NAME");
            if(!bundle.endsWith(project->first("QMAKE_BUNDLE_EXTENSION")))
                bundle += project->first("QMAKE_BUNDLE_EXTENSION");
        } else if(project->first("TEMPLATE") == "app" && project->isActiveConfig("app_bundle")) {
            bundle = project->first("TARGET");
            if(!project->isEmpty("QMAKE_APPLICATION_BUNDLE_NAME"))
                bundle = project->first("QMAKE_APPLICATION_BUNDLE_NAME");
            if(!bundle.endsWith(".app"))
                bundle += ".app";
            if(project->isEmpty("QMAKE_BUNDLE_LOCATION"))
                project->values("QMAKE_BUNDLE_LOCATION").append("Contents/MacOS");
            project->values("QMAKE_PKGINFO").append(project->first("DESTDIR") + bundle + "/Contents/PkgInfo");
            project->values("QMAKE_BUNDLE_RESOURCE_FILE").append(project->first("DESTDIR") + bundle + "/Contents/Resources/empty.lproj");
        } else if(project->first("TEMPLATE") == "lib" && !project->isActiveConfig("staticlib") &&
                  ((!project->isActiveConfig("plugin") && project->isActiveConfig("lib_bundle")) ||
                   (project->isActiveConfig("plugin") && project->isActiveConfig("plugin_bundle")))) {
            bundle = project->first("TARGET");
            if(project->isActiveConfig("plugin")) {
                if(!project->isEmpty("QMAKE_PLUGIN_BUNDLE_NAME"))
                    bundle = project->first("QMAKE_PLUGIN_BUNDLE_NAME");
                if (project->isEmpty("QMAKE_BUNDLE_EXTENSION"))
                    project->values("QMAKE_BUNDLE_EXTENSION").append(".plugin");
                if (!bundle.endsWith(project->first("QMAKE_BUNDLE_EXTENSION")))
                    bundle += project->first("QMAKE_BUNDLE_EXTENSION");
                if(project->isEmpty("QMAKE_BUNDLE_LOCATION"))
                    project->values("QMAKE_BUNDLE_LOCATION").append("Contents/MacOS");
            } else {
                if(!project->isEmpty("QMAKE_FRAMEWORK_BUNDLE_NAME"))
                    bundle = project->first("QMAKE_FRAMEWORK_BUNDLE_NAME");
                if (project->isEmpty("QMAKE_BUNDLE_EXTENSION"))
                    project->values("QMAKE_BUNDLE_EXTENSION").append(".framework");
                if (!bundle.endsWith(project->first("QMAKE_BUNDLE_EXTENSION")))
                    bundle += project->first("QMAKE_BUNDLE_EXTENSION");
            }
        }
        if(!bundle.isEmpty()) {
            project->values("QMAKE_BUNDLE") = ProStringList(bundle);
        } else {
            project->values("QMAKE_BUNDLE").clear();
            project->values("QMAKE_BUNDLE_LOCATION").clear();
        }
    } else { //no bundling here
        project->values("QMAKE_BUNDLE").clear();
        project->values("QMAKE_BUNDLE_LOCATION").clear();
    }

    init2();
    project->values("QMAKE_INTERNAL_PRL_LIBS") << "QMAKE_LIBS";
    ProString target = project->first("TARGET");
    int slsh = target.lastIndexOf(Option::dir_sep);
    if (slsh != -1)
        target.chopFront(slsh + 1);
    project->values("LIB_TARGET").prepend(target);
    if(!project->isEmpty("QMAKE_MAX_FILES_PER_AR")) {
        bool ok;
        int max_files = project->first("QMAKE_MAX_FILES_PER_AR").toInt(&ok);
        ProStringList ar_sublibs, objs = project->values("OBJECTS");
        if(ok && max_files > 5 && max_files < (int)objs.count()) {
            QString lib;
            for(int i = 0, obj_cnt = 0, lib_cnt = 0; i != objs.size(); ++i) {
                if((++obj_cnt) >= max_files) {
                    if(lib_cnt) {
                        lib.sprintf("lib%s-tmp%d.a",
                                    project->first("QMAKE_ORIG_TARGET").toLatin1().constData(), lib_cnt);
                        ar_sublibs << lib;
                        obj_cnt = 0;
                    }
                    lib_cnt++;
                }
            }
        }
        if(!ar_sublibs.isEmpty()) {
            project->values("QMAKE_AR_SUBLIBS") = ar_sublibs;
            project->values("QMAKE_INTERNAL_PRL_LIBS") << "QMAKE_AR_SUBLIBS";
        }
    }
}
Пример #12
0
void
UnixMakefileGenerator::processPrlFiles()
{
    const QString libArg = project->first("QMAKE_L_FLAG").toQString();
    QList<QMakeLocalFileName> libdirs, frameworkdirs;
    int libidx = 0, fwidx = 0;
    foreach (const ProString &dlib, project->values("QMAKE_DEFAULT_LIBDIRS"))
        libdirs.append(QMakeLocalFileName(dlib.toQString()));
    frameworkdirs.append(QMakeLocalFileName("/System/Library/Frameworks"));
    frameworkdirs.append(QMakeLocalFileName("/Library/Frameworks"));
    static const char * const lflags[] = { "QMAKE_LIBS", "QMAKE_LIBS_PRIVATE", 0 };
    for (int i = 0; lflags[i]; i++) {
        ProStringList &l = project->values(lflags[i]);
        for(int lit = 0; lit < l.size(); ++lit) {
            QString opt = l.at(lit).trimmed().toQString();
            if(opt.startsWith("-")) {
                if (opt.startsWith(libArg)) {
                    QMakeLocalFileName l(opt.mid(libArg.length()));
                    if(!libdirs.contains(l))
                       libdirs.insert(libidx++, l);
                } else if(opt.startsWith("-l")) {
                    QString lib = opt.right(opt.length() - 2);
                    QString prl_ext = project->first(ProKey("QMAKE_" + lib.toUpper() + "_SUFFIX")).toQString();
                    for(int dep_i = 0; dep_i < libdirs.size(); ++dep_i) {
                        const QMakeLocalFileName &lfn = libdirs[dep_i];
                        if(!project->isActiveConfig("compile_libtool")) { //give them the .libs..
                            QString la = lfn.local() + Option::dir_sep + project->values("QMAKE_PREFIX_SHLIB").first() + lib + Option::libtool_ext;
                            if(exists(la) && QFile::exists(lfn.local() + Option::dir_sep + ".libs")) {
                                QString dot_libs = lfn.real() + Option::dir_sep + ".libs";
                                l.append("-L" + dot_libs);
                                libdirs.insert(libidx++, QMakeLocalFileName(dot_libs));
                            }
                        }

                        QString prl = lfn.local() + Option::dir_sep + project->values("QMAKE_PREFIX_SHLIB").first() + lib + prl_ext;
                        if(processPrlFile(prl)) {
                            if(prl.startsWith(lfn.local()))
                                prl.replace(0, lfn.local().length(), lfn.real());
                            opt = linkLib(prl, lib);
                            break;
                        }
                    }
                } else if (target_mode == TARG_MAC_MODE && opt.startsWith("-F")) {
                    QMakeLocalFileName f(opt.right(opt.length()-2));
                    if(!frameworkdirs.contains(f))
                        frameworkdirs.insert(fwidx++, f);
                } else if (target_mode == TARG_MAC_MODE && opt.startsWith("-framework")) {
                    if(opt.length() > 11)
                        opt = opt.mid(11);
                    else
                        opt = l.at(++lit).toQString();
                    opt = opt.trimmed();
                    foreach (const QMakeLocalFileName &dir, frameworkdirs) {
                        QString prl = dir.local() + "/" + opt + ".framework/" + opt + Option::prl_ext;
                        if(processPrlFile(prl))
                            break;
                    }
                }
            } else if(!opt.isNull()) {
                QString lib = opt;
                processPrlFile(lib);
#if 0
                if(ret)
                    opt = linkLib(lib, "");
#endif
                if(!opt.isEmpty())
                    for (int k = 0; k < l.size(); ++k)
                        l[k] = l.at(k).toQString().replace(lib, opt);
            }

            ProStringList &prl_libs = project->values("QMAKE_CURRENT_PRL_LIBS");
            if(!prl_libs.isEmpty()) {
                for(int prl = 0; prl < prl_libs.size(); ++prl)
                    l.insert(lit+prl+1, escapeFilePath(prl_libs.at(prl).toQString()));
                prl_libs.clear();
            }
        }