diff --git a/src/plugins/cpptools/cppmodelmanagerinterface.cpp b/src/plugins/cpptools/cppmodelmanagerinterface.cpp
index d6a4158b0c6ffec51549b67a24ee8ff33999a4b2..a7b501136715f8e8f5b5b4e3665f268095adf4b3 100644
--- a/src/plugins/cpptools/cppmodelmanagerinterface.cpp
+++ b/src/plugins/cpptools/cppmodelmanagerinterface.cpp
@@ -31,11 +31,7 @@
 
 #include <cplusplus/pp-engine.h>
 
-#include <projectexplorer/headerpath.h>
-#include <projectexplorer/toolchain.h>
-
 using namespace CppTools;
-using namespace ProjectExplorer;
 
 /*!
     \enum CppTools::CppModelManagerInterface::ProgressNotificationMode
diff --git a/src/plugins/cpptools/cppprojects.cpp b/src/plugins/cpptools/cppprojects.cpp
index 058bf27e633601a04d3230ffe86e03a654c790ca..c9bb67bdfa27a4f94897ae8b88c43dfd4670ef35 100644
--- a/src/plugins/cpptools/cppprojects.cpp
+++ b/src/plugins/cpptools/cppprojects.cpp
@@ -30,11 +30,17 @@
 #include "cppprojects.h"
 
 #include <projectexplorer/headerpath.h>
+#include <projectexplorer/kit.h>
+#include <projectexplorer/kitinformation.h>
+#include <projectexplorer/kitmanager.h>
+#include <projectexplorer/projectexplorerconstants.h>
+#include <projectexplorer/target.h>
 
 #include <QSet>
 #include <QTextStream>
 
-namespace CppTools {
+using namespace CppTools;
+using namespace ProjectExplorer;
 
 ProjectPart::ProjectPart()
     : project(0)
@@ -44,7 +50,6 @@ ProjectPart::ProjectPart()
     , qtVersion(UnknownQt)
     , cWarningFlags(ProjectExplorer::ToolChain::WarningsDefault)
     , cxxWarningFlags(ProjectExplorer::ToolChain::WarningsDefault)
-
 {
 }
 
@@ -103,6 +108,11 @@ void ProjectPart::evaluateToolchain(const ProjectExplorer::ToolChain *tc,
     toolchainDefines = tc->predefinedMacros(cxxflags);
 }
 
+ProjectPart::Ptr ProjectPart::copy() const
+{
+    return Ptr(new ProjectPart(*this));
+}
+
 QByteArray ProjectPart::readProjectConfigFile(const ProjectPart::Ptr &part)
 {
     QByteArray result;
@@ -208,4 +218,222 @@ const QByteArray ProjectInfo::defines() const
     return m_defines;
 }
 
-} // namespace CppTools
+namespace {
+class ProjectFileCategorizer
+{
+public:
+    ProjectFileCategorizer(const QString &partName, const QStringList &files)
+        : m_partName(partName)
+    {
+        using CppTools::ProjectFile;
+
+        QStringList cHeaders, cxxHeaders;
+
+        foreach (const QString &file, files) {
+            switch (ProjectFile::classify(file)) {
+            case ProjectFile::CSource: m_cSources += file; break;
+            case ProjectFile::CHeader: cHeaders += file; break;
+            case ProjectFile::CXXSource: m_cxxSources += file; break;
+            case ProjectFile::CXXHeader: cxxHeaders += file; break;
+            case ProjectFile::ObjCSource: m_objcSources += file; break;
+            case ProjectFile::ObjCXXSource: m_objcxxSources += file; break;
+            default:
+                continue;
+            }
+        }
+
+        const bool hasC = !m_cSources.isEmpty();
+        const bool hasCxx = !m_cxxSources.isEmpty();
+        const bool hasObjc = !m_objcSources.isEmpty();
+        const bool hasObjcxx = !m_objcxxSources.isEmpty();
+
+        if (hasObjcxx)
+            m_objcxxSources += cxxHeaders + cHeaders;
+        if (hasCxx)
+            m_cxxSources += cxxHeaders + cHeaders;
+        else if (!hasObjcxx)
+            m_cxxSources += cxxHeaders;
+        if (hasObjc)
+            m_objcSources += cHeaders;
+        if (hasC || (!hasObjc && !hasObjcxx && !hasCxx))
+            m_cSources += cHeaders;
+
+        m_partCount =
+                (m_cSources.isEmpty() ? 0 : 1) +
+                (m_cxxSources.isEmpty() ? 0 : 1) +
+                (m_objcSources.isEmpty() ? 0 : 1) +
+                (m_objcxxSources.isEmpty() ? 0 : 1);
+    }
+
+    bool hasCSources() const { return !m_cSources.isEmpty(); }
+    bool hasCxxSources() const { return !m_cxxSources.isEmpty(); }
+    bool hasObjcSources() const { return !m_objcSources.isEmpty(); }
+    bool hasObjcxxSources() const { return !m_objcxxSources.isEmpty(); }
+
+    QStringList cSources() const { return m_cSources; }
+    QStringList cxxSources() const { return m_cxxSources; }
+    QStringList objcSources() const { return m_objcSources; }
+    QStringList objcxxSources() const { return m_objcxxSources; }
+
+    bool hasMultipleParts() const { return m_partCount > 1; }
+    bool hasNoParts() const { return m_partCount == 0; }
+
+    QString partName(const QString &languageName) const
+    {
+        if (hasMultipleParts())
+            return QString::fromLatin1("%1 (%2)").arg(m_partName).arg(languageName);
+
+        return m_partName;
+    }
+
+private:
+    QString m_partName;
+    QStringList m_cSources, m_cxxSources, m_objcSources, m_objcxxSources;
+    int m_partCount;
+};
+} // anonymous namespace
+
+ProjectPartBuilder::ProjectPartBuilder(ProjectInfo &pInfo)
+    : m_templatePart(new ProjectPart)
+    , m_pInfo(pInfo)
+{
+    m_templatePart->project = pInfo.project();
+    m_templatePart->displayName = pInfo.project()->displayName();
+    m_templatePart->projectFile = pInfo.project()->projectFilePath().toString();
+}
+
+void ProjectPartBuilder::setQtVersion(ProjectPart::QtVersion qtVersion)
+{
+    m_templatePart->qtVersion = qtVersion;
+}
+
+void ProjectPartBuilder::setCFlags(const QStringList &flags)
+{
+    m_cFlags = flags;
+}
+
+void ProjectPartBuilder::setCxxFlags(const QStringList &flags)
+{
+    m_cxxFlags = flags;
+}
+
+void ProjectPartBuilder::setDefines(const QByteArray &defines)
+{
+    m_templatePart->projectDefines = defines;
+}
+
+void ProjectPartBuilder::setHeaderPaths(const ProjectPart::HeaderPaths &headerPaths)
+{
+    m_templatePart->headerPaths = headerPaths;
+}
+
+void ProjectPartBuilder::setIncludePaths(const QStringList &includePaths)
+{
+    m_templatePart->headerPaths.clear();
+
+    foreach (const QString &includeFile, includePaths) {
+        ProjectPart::HeaderPath hp(includeFile, ProjectPart::HeaderPath::IncludePath);
+
+        // The simple project managers are utterly ignorant of frameworks on OSX, and won't report
+        // framework paths. The work-around is to check if the include path ends in ".framework",
+        // and if so, add the parent directory as framework path.
+        if (includeFile.endsWith(QLatin1String(".framework"))) {
+            const int slashIdx = includeFile.lastIndexOf(QLatin1Char('/'));
+            if (slashIdx != -1) {
+                hp = ProjectPart::HeaderPath(includeFile.left(slashIdx),
+                                             ProjectPart::HeaderPath::FrameworkPath);
+                continue;
+            }
+        }
+
+        m_templatePart->headerPaths += hp;
+    }
+}
+
+void ProjectPartBuilder::setPreCompiledHeaders(const QStringList &pchs)
+{
+    m_templatePart->precompiledHeaders = pchs;
+}
+
+void ProjectPartBuilder::setProjectFile(const QString &projectFile)
+{
+    m_templatePart->projectFile = projectFile;
+}
+
+void ProjectPartBuilder::setDisplayName(const QString &displayName)
+{
+    m_templatePart->displayName = displayName;
+}
+
+void ProjectPartBuilder::setConfigFileName(const QString &configFileName)
+{
+    m_templatePart->projectConfigFile = configFileName;
+}
+
+QList<Core::Id> ProjectPartBuilder::createProjectPartsForFiles(const QStringList &files)
+{
+    QList<Core::Id> languages;
+
+    ProjectFileCategorizer cat(m_templatePart->displayName, files);
+    if (cat.hasNoParts())
+        return languages;
+
+    using CppTools::ProjectFile;
+    using CppTools::ProjectPart;
+
+    if (cat.hasCSources()) {
+        createProjectPart(cat.cSources(),
+                          cat.partName(QCoreApplication::translate("CppTools", "C11")),
+                          ProjectPart::C11,
+                          ProjectPart::CXX11);
+        // TODO: there is no C...
+//        languages += ProjectExplorer::Constants::LANG_C;
+    }
+    if (cat.hasObjcSources()) {
+        createProjectPart(cat.objcSources(),
+                          cat.partName(QCoreApplication::translate("CppTools", "Obj-C11")),
+                          ProjectPart::C11,
+                          ProjectPart::CXX11);
+        // TODO: there is no Ojective-C...
+//        languages += ProjectExplorer::Constants::LANG_OBJC;
+    }
+    if (cat.hasCxxSources()) {
+        createProjectPart(cat.cxxSources(),
+                          cat.partName(QCoreApplication::translate("CppTools", "C++11")),
+                          ProjectPart::C11,
+                          ProjectPart::CXX11);
+        languages += ProjectExplorer::Constants::LANG_CXX;
+    }
+    if (cat.hasObjcxxSources()) {
+        createProjectPart(cat.objcxxSources(),
+                          cat.partName(QCoreApplication::translate("CppTools", "Obj-C++11")),
+                          ProjectPart::C11,
+                          ProjectPart::CXX11);
+        // TODO: there is no Objective-C++...
+        languages += ProjectExplorer::Constants::LANG_CXX;
+    }
+
+    return languages;
+}
+
+void ProjectPartBuilder::createProjectPart(const QStringList &theSources,
+                                           const QString &partName,
+                                           ProjectPart::CVersion cVersion,
+                                           ProjectPart::CXXVersion cxxVersion)
+{
+    CppTools::ProjectPart::Ptr part(m_templatePart->copy());
+    part->displayName = partName;
+
+    Kit *k = part->project->activeTarget()->kit();
+    if (ToolChain *tc = ToolChainKitInformation::toolChain(k))
+        part->evaluateToolchain(tc, m_cFlags, m_cxxFlags, SysRootKitInformation::sysRoot(k));
+
+    part->cVersion = cVersion;
+    part->cxxVersion = cxxVersion;
+
+    CppTools::ProjectFileAdder adder(part->files);
+    foreach (const QString &file, theSources)
+        adder.maybeAdd(file);
+
+    m_pInfo.appendProjectPart(part);
+}
diff --git a/src/plugins/cpptools/cppprojects.h b/src/plugins/cpptools/cppprojects.h
index da11f695ab1fa94b2009e8b6b0579a7f4a79e5d6..17ef8b34a2e3115b0b3ea2866f8608f24d6c8de3 100644
--- a/src/plugins/cpptools/cppprojects.h
+++ b/src/plugins/cpptools/cppprojects.h
@@ -43,18 +43,7 @@ namespace CppTools {
 
 class CPPTOOLS_EXPORT ProjectPart
 {
-public:
-    typedef QSharedPointer<ProjectPart> Ptr;
-
-public:
-    ProjectPart();
-
-    void evaluateToolchain(const ProjectExplorer::ToolChain *tc,
-                           const QStringList &cxxflags,
-                           const QStringList &cflags,
-                           const Utils::FileName &sysRoot);
-
-public:
+public: // Types
     enum CVersion {
         C89,
         C99,
@@ -84,11 +73,12 @@ public:
         Qt5 = 2
     };
 
-    class HeaderPath
-    {
-    public:
+    typedef QSharedPointer<ProjectPart> Ptr;
+
+    struct HeaderPath {
         enum Type { InvalidPath, IncludePath, FrameworkPath };
 
+    public:
         QString path;
         Type type;
 
@@ -106,10 +96,19 @@ public:
     };
     typedef QList<HeaderPath> HeaderPaths;
 
-public:
+public: // methods
+    ProjectPart();
+
+    void evaluateToolchain(const ProjectExplorer::ToolChain *tc,
+                           const QStringList &cxxflags,
+                           const QStringList &cflags,
+                           const Utils::FileName &sysRoot);
+
+    Ptr copy() const;
+
     static QByteArray readProjectConfigFile(const ProjectPart::Ptr &part);
 
-public:
+public: // fields
     QString displayName;
     QString projectFile;
     ProjectExplorer::Project *project;
@@ -159,6 +158,34 @@ private:
     QByteArray m_defines;
 };
 
+class CPPTOOLS_EXPORT ProjectPartBuilder
+{
+public:
+    ProjectPartBuilder(ProjectInfo &m_pInfo);
+
+    void setQtVersion(ProjectPart::QtVersion qtVersion);
+    void setCFlags(const QStringList &flags);
+    void setCxxFlags(const QStringList &flags);
+    void setDefines(const QByteArray &defines);
+    void setHeaderPaths(const ProjectPart::HeaderPaths &headerPaths);
+    void setIncludePaths(const QStringList &includePaths);
+    void setPreCompiledHeaders(const QStringList &pchs);
+    void setProjectFile(const QString &projectFile);
+    void setDisplayName(const QString &displayName);
+    void setConfigFileName(const QString &configFileName);
+
+    QList<Core::Id> createProjectPartsForFiles(const QStringList &files);
+
+private:
+    void createProjectPart(const QStringList &theSources, const QString &partName,
+                           ProjectPart::CVersion cVersion, ProjectPart::CXXVersion cxxVersion);
+
+private:
+    ProjectPart::Ptr m_templatePart;
+    ProjectInfo &m_pInfo;
+    QStringList m_cFlags, m_cxxFlags;
+};
+
 } // namespace CppTools
 
 #endif // CPPPROJECTPART_H
diff --git a/src/plugins/genericprojectmanager/genericproject.cpp b/src/plugins/genericprojectmanager/genericproject.cpp
index a460e8537f5b61a8894462ba1079658c1bae08ab..463c1f65a5fa4f1dba846bbd3072ee12d49ea991 100644
--- a/src/plugins/genericprojectmanager/genericproject.cpp
+++ b/src/plugins/genericprojectmanager/genericproject.cpp
@@ -266,47 +266,7 @@ void GenericProject::refresh(RefreshOptions options)
     if (options & Files)
         m_rootNode->refresh(oldFileList);
 
-    CppTools::CppModelManagerInterface *modelManager =
-        CppTools::CppModelManagerInterface::instance();
-
-    if (modelManager) {
-        CppTools::ProjectInfo pinfo = modelManager->projectInfo(this);
-        pinfo.clearProjectParts();
-        CppTools::ProjectPart::Ptr part(new CppTools::ProjectPart);
-        part->project = this;
-        part->displayName = displayName();
-        part->projectFile = projectFilePath().toString();
-
-        foreach (const QString &inc, projectIncludePaths())
-            part->headerPaths += CppTools::ProjectPart::HeaderPath(
-                        inc, CppTools::ProjectPart::HeaderPath::IncludePath);
-
-        Kit *k = activeTarget() ? activeTarget()->kit() : KitManager::defaultKit();
-        if (ToolChain *tc = ToolChainKitInformation::toolChain(k)) {
-            QStringList cflags;
-            QStringList cxxflags;
-            cxxflags << QLatin1String("-std=c++11");
-
-            part->evaluateToolchain(tc, cxxflags, cflags,
-                                    SysRootKitInformation::sysRoot(k));
-        }
-
-        part->projectConfigFile = configFileName();
-
-        // ### add _defines.
-
-        // Add any C/C++ files to be parsed
-        CppTools::ProjectFileAdder adder(part->files);
-        foreach (const QString &file, files())
-            adder.maybeAdd(file);
-
-        m_codeModelFuture.cancel();
-
-        pinfo.appendProjectPart(part);
-        setProjectLanguage(ProjectExplorer::Constants::LANG_CXX, !part->files.isEmpty());
-
-        m_codeModelFuture = modelManager->updateProjectInfo(pinfo);
-    }
+    refreshCppCodeModel();
 }
 
 /**
@@ -364,6 +324,31 @@ QStringList GenericProject::processEntries(const QStringList &paths,
     return absolutePaths;
 }
 
+void GenericProject::refreshCppCodeModel()
+{
+    CppTools::CppModelManagerInterface *modelManager =
+            CppTools::CppModelManagerInterface::instance();
+
+    if (!modelManager)
+        return;
+
+    m_codeModelFuture.cancel();
+
+    CppTools::ProjectInfo pInfo = modelManager->projectInfo(this);
+    pInfo.clearProjectParts();
+
+    CppTools::ProjectPartBuilder ppBuilder(pInfo);
+    ppBuilder.setIncludePaths(projectIncludePaths());
+    ppBuilder.setConfigFileName(configFileName());
+    ppBuilder.setCxxFlags(QStringList() << QLatin1String("-std=c++11"));
+
+    const QList<Core::Id> languages = ppBuilder.createProjectPartsForFiles(files());
+    foreach (Core::Id language, languages)
+        setProjectLanguage(language, true);
+
+    m_codeModelFuture = modelManager->updateProjectInfo(pInfo);
+}
+
 QStringList GenericProject::projectIncludePaths() const
 {
     return m_projectIncludePaths;
diff --git a/src/plugins/genericprojectmanager/genericproject.h b/src/plugins/genericprojectmanager/genericproject.h
index 9a4087b1c1dc855b699dcf5806e04717d5148596..995464317956403a239f4e538a597df3c79e836b 100644
--- a/src/plugins/genericprojectmanager/genericproject.h
+++ b/src/plugins/genericprojectmanager/genericproject.h
@@ -94,6 +94,8 @@ private:
     QStringList processEntries(const QStringList &paths,
                                QHash<QString, QString> *map = 0) const;
 
+    void refreshCppCodeModel();
+
     Manager *m_manager;
     QString m_fileName;
     QString m_filesFileName;
diff --git a/src/plugins/genericprojectmanager/genericprojectplugin.h b/src/plugins/genericprojectmanager/genericprojectplugin.h
index 5ce2212e70d4ef1b87da4e125d63b32eaf747a24..a56a1e450ba5cf5a3567248c18ea84a50ac8c917 100644
--- a/src/plugins/genericprojectmanager/genericprojectplugin.h
+++ b/src/plugins/genericprojectmanager/genericprojectplugin.h
@@ -60,6 +60,8 @@ private slots:
 #ifdef WITH_TESTS
 private slots:
     void test_simple();
+    void test_mixed1();
+    void test_mixed2();
 #endif // WITH_TESTS
 
 private:
diff --git a/src/plugins/genericprojectmanager/genericprojectplugin_test.cpp b/src/plugins/genericprojectmanager/genericprojectplugin_test.cpp
index 32a9c656df6a6039209716c7a99a0cd0a7b1c22a..ec1770887ab3e2ed34bb792a176d700e933dde4a 100644
--- a/src/plugins/genericprojectmanager/genericprojectplugin_test.cpp
+++ b/src/plugins/genericprojectmanager/genericprojectplugin_test.cpp
@@ -85,26 +85,124 @@ private:
 };
 } // anonymous namespace
 
-void GenericProjectPlugin::test_simple()
+static ProjectInfo setupProject(const QByteArray &projectFile, const QByteArray &mainFile,
+                                ProjectExplorerHelper &pHelper)
 {
     CppModelManagerHelper cppHelper;
+    Project *project = pHelper.openProject(projectFilePath(_(projectFile)));
+    if (!project)
+        return ProjectInfo();
 
-    QString projectFile = _("testdata_simpleproject/simpleproject.creator");
-    ProjectExplorerHelper pHelper;
-    Project *project = pHelper.openProject(projectFilePath(projectFile));
-    QVERIFY(project);
-
-    QString mainFile = projectFilePath(_("testdata_simpleproject/main.cpp"));
-    cppHelper.waitForSourceFilesRefreshed(mainFile);
+    // Wait only for a single file: we don't really care if the file is refreshed or not, but at
+    // this point we know that the C++ model manager got notified of all project parts and we can
+    // retrieve them for inspection.
+    cppHelper.waitForSourceFilesRefreshed(projectFilePath(_(mainFile)));
 
     CppModelManagerInterface *mm = cppHelper.cppModelManager();
-    ProjectInfo pInfo = mm->projectInfo(project);
+    return mm->projectInfo(project);
+}
 
+void GenericProjectPlugin::test_simple()
+{
+    ProjectExplorerHelper pHelper;
+
+    const QByteArray mainFile("testdata_simpleproject/main.cpp");
+    ProjectInfo pInfo(
+                setupProject("testdata_simpleproject/simpleproject.creator", mainFile, pHelper));
+    QVERIFY(pInfo);
     QCOMPARE(pInfo.projectParts().size(), 1);
 
     ProjectPart::Ptr pPart = pInfo.projectParts().first();
     QVERIFY(pPart);
     QCOMPARE(pPart->files.size(), 1);
-    QCOMPARE(pPart->files.first().path, mainFile);
+    QCOMPARE(pPart->files.first().path, projectFilePath(_(mainFile)));
     QCOMPARE(pPart->files.first().kind, ProjectFile::CXXSource);
 }
+
+static QStringList simplify(const QList<CppTools::ProjectFile> &files, const QString &prefix)
+{
+    QStringList result;
+
+    foreach (const CppTools::ProjectFile &file, files) {
+        if (file.path.startsWith(prefix))
+            result.append(file.path.mid(prefix.size()));
+        else
+            result.append(file.path);
+    }
+
+    return result;
+}
+
+void GenericProjectPlugin::test_mixed1()
+{
+    ProjectExplorerHelper pHelper;
+    ProjectInfo pInfo(
+                setupProject("testdata_mixedproject1/mixedproject1.creator",
+                             "testdata_mixedproject1/main.cpp",
+                             pHelper));
+    QVERIFY(pInfo);
+    QCOMPARE(pInfo.projectParts().size(), 3);
+
+    QList<ProjectPart::Ptr> parts = pInfo.projectParts();
+    std::sort(parts.begin(), parts.end(), [](const ProjectPart::Ptr &p1,
+                                             const ProjectPart::Ptr &p2) {
+        return p1->displayName < p2->displayName;
+    });
+
+    QStringList part0files = simplify(parts[0]->files,projectFilePath(_("testdata_mixedproject1/")));
+    QStringList part1files = simplify(parts[1]->files,projectFilePath(_("testdata_mixedproject1/")));
+    QStringList part2files = simplify(parts[2]->files,projectFilePath(_("testdata_mixedproject1/")));
+
+    QCOMPARE(parts[0]->displayName, _("mixedproject1 (C++11)"));
+    QCOMPARE(parts[0]->files.size(), 4);
+    QVERIFY(part0files.contains(_("main.cpp")));
+    QVERIFY(part0files.contains(_("header.h")));
+    QVERIFY(part0files.contains(_("MyViewController.h")));
+    QVERIFY(part0files.contains(_("Glue.h")));
+
+    QCOMPARE(parts[1]->displayName, _("mixedproject1 (Obj-C++11)"));
+    QCOMPARE(parts[1]->files.size(), 4);
+    QVERIFY(part1files.contains(_("Glue.mm")));
+    QVERIFY(part1files.contains(_("header.h")));
+    QVERIFY(part1files.contains(_("MyViewController.h")));
+    QVERIFY(part1files.contains(_("Glue.h")));
+
+    QCOMPARE(parts[2]->displayName, _("mixedproject1 (Obj-C11)"));
+    QCOMPARE(parts[2]->files.size(), 1);
+    QVERIFY(part2files.contains(_("MyViewController.m")));
+    // No .h files here, because the mime-type for .h files is.....
+    //
+    // wait for it...
+    //
+    // C++!
+    // (See 1c7da3d83c9bb35064ae6b9052cbf1c6bff1395e.)
+}
+
+void GenericProjectPlugin::test_mixed2()
+{
+    ProjectExplorerHelper pHelper;
+    ProjectInfo pInfo(
+                setupProject("testdata_mixedproject2/mixedproject2.creator",
+                             "testdata_mixedproject2/main.cpp",
+                             pHelper));
+    QVERIFY(pInfo);
+    QCOMPARE(pInfo.projectParts().size(), 2);
+
+    QList<ProjectPart::Ptr> parts = pInfo.projectParts();
+    std::sort(parts.begin(), parts.end(), [](const ProjectPart::Ptr &p1,
+                                             const ProjectPart::Ptr &p2) {
+        return p1->displayName < p2->displayName;
+    });
+
+    QStringList part0files = simplify(parts[0]->files,projectFilePath(_("testdata_mixedproject2/")));
+    QStringList part1files = simplify(parts[1]->files,projectFilePath(_("testdata_mixedproject2/")));
+
+    QCOMPARE(parts[0]->displayName, _("mixedproject2 (C++11)"));
+    QCOMPARE(parts[0]->files.size(), 2);
+    QVERIFY(part0files.contains(_("main.cpp")));
+    QVERIFY(part0files.contains(_("header.hpp")));
+
+    QCOMPARE(parts[1]->displayName, _("mixedproject2 (C11)"));
+    QCOMPARE(parts[1]->files.size(), 1);
+    QVERIFY(part1files.contains(_("impl.c")));
+}
diff --git a/tests/genericprojectmanager/testdata_mixedproject1/Glue.h b/tests/genericprojectmanager/testdata_mixedproject1/Glue.h
new file mode 100644
index 0000000000000000000000000000000000000000..dd39049addb12ac46d710b17e38689973d7ef40f
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject1/Glue.h
@@ -0,0 +1,10 @@
+#ifndef GLUE_H
+#define GLUE_H
+
+struct Glue {
+    struct it {
+        static void together();
+    };
+};
+
+#endif // GLUE_H
diff --git a/tests/genericprojectmanager/testdata_mixedproject1/Glue.mm b/tests/genericprojectmanager/testdata_mixedproject1/Glue.mm
new file mode 100644
index 0000000000000000000000000000000000000000..452d04961653b8bd466f0197cab46d49f4d37a55
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject1/Glue.mm
@@ -0,0 +1,8 @@
+#include "Glue.h"
+
+@class NSApp;
+
+void Glue::it::together()
+{
+    [[NSApp dockTile] setContentView:nil];
+}
diff --git a/tests/genericprojectmanager/testdata_mixedproject1/MyViewController.h b/tests/genericprojectmanager/testdata_mixedproject1/MyViewController.h
new file mode 100644
index 0000000000000000000000000000000000000000..533cfb6578bea965255467b9cc5e99664b52e487
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject1/MyViewController.h
@@ -0,0 +1,5 @@
+@class NSViewController;
+
+@interface AppDelegate : NSViewController
+
+@end
diff --git a/tests/genericprojectmanager/testdata_mixedproject1/MyViewController.m b/tests/genericprojectmanager/testdata_mixedproject1/MyViewController.m
new file mode 100644
index 0000000000000000000000000000000000000000..99277051ceb47a5feb9962fbcc5aa20528973ec1
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject1/MyViewController.m
@@ -0,0 +1,7 @@
+#import "MyViewController.h"
+
+@interface MyViewController ()
+@end
+
+@implementation MyViewController
+@end
diff --git a/tests/genericprojectmanager/testdata_mixedproject1/header.h b/tests/genericprojectmanager/testdata_mixedproject1/header.h
new file mode 100644
index 0000000000000000000000000000000000000000..689ec0387103e029db8d0fa0ed5c278c88674860
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject1/header.h
@@ -0,0 +1,4 @@
+#ifndef HEADER_H
+#define HEADER_H
+
+#endif // HEADER_H
diff --git a/tests/genericprojectmanager/testdata_mixedproject1/main.cpp b/tests/genericprojectmanager/testdata_mixedproject1/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..5047a34e393afabd94f779966acc69b8edf9570d
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject1/main.cpp
@@ -0,0 +1,3 @@
+int main()
+{
+}
diff --git a/tests/genericprojectmanager/testdata_mixedproject1/mixedproject1.config b/tests/genericprojectmanager/testdata_mixedproject1/mixedproject1.config
new file mode 100644
index 0000000000000000000000000000000000000000..9dcf447363f7e2c3be97678b048088d85987db66
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject1/mixedproject1.config
@@ -0,0 +1 @@
+// Nothing to be seen, move along.
diff --git a/tests/genericprojectmanager/testdata_mixedproject1/mixedproject1.creator b/tests/genericprojectmanager/testdata_mixedproject1/mixedproject1.creator
new file mode 100644
index 0000000000000000000000000000000000000000..e94cbbd3027df32cb00f4fca093d5c72d9696a85
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject1/mixedproject1.creator
@@ -0,0 +1 @@
+[General]
diff --git a/tests/genericprojectmanager/testdata_mixedproject1/mixedproject1.files b/tests/genericprojectmanager/testdata_mixedproject1/mixedproject1.files
new file mode 100644
index 0000000000000000000000000000000000000000..52ae971ccdb9b114e045cc4f058cd78440bd13d2
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject1/mixedproject1.files
@@ -0,0 +1,6 @@
+main.cpp
+header.h
+MyViewController.h
+MyViewController.m
+Glue.h
+Glue.mm
diff --git a/tests/genericprojectmanager/testdata_mixedproject1/mixedproject1.includes b/tests/genericprojectmanager/testdata_mixedproject1/mixedproject1.includes
new file mode 100644
index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391
diff --git a/tests/genericprojectmanager/testdata_mixedproject2/header.hpp b/tests/genericprojectmanager/testdata_mixedproject2/header.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..ebc2cf627a62d6b02923730f47eab53c716d630b
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject2/header.hpp
@@ -0,0 +1,6 @@
+#ifndef HEADER_HPP
+#define HEADER_HPP
+
+extern "C" void impl();
+
+#endif // HEADER_HPP
diff --git a/tests/genericprojectmanager/testdata_mixedproject2/impl.c b/tests/genericprojectmanager/testdata_mixedproject2/impl.c
new file mode 100644
index 0000000000000000000000000000000000000000..d514ce6ea426e5b7c41e0be7329ee3a7df50691c
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject2/impl.c
@@ -0,0 +1,4 @@
+void impl()
+{
+    abort();
+}
diff --git a/tests/genericprojectmanager/testdata_mixedproject2/main.cpp b/tests/genericprojectmanager/testdata_mixedproject2/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..7dfe0b19faaca7380f668774111489554dc4f95d
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject2/main.cpp
@@ -0,0 +1,6 @@
+#include "header.hpp"
+
+int main()
+{
+    impl();
+}
diff --git a/tests/genericprojectmanager/testdata_mixedproject2/mixedproject2.config b/tests/genericprojectmanager/testdata_mixedproject2/mixedproject2.config
new file mode 100644
index 0000000000000000000000000000000000000000..9dcf447363f7e2c3be97678b048088d85987db66
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject2/mixedproject2.config
@@ -0,0 +1 @@
+// Nothing to be seen, move along.
diff --git a/tests/genericprojectmanager/testdata_mixedproject2/mixedproject2.creator b/tests/genericprojectmanager/testdata_mixedproject2/mixedproject2.creator
new file mode 100644
index 0000000000000000000000000000000000000000..e94cbbd3027df32cb00f4fca093d5c72d9696a85
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject2/mixedproject2.creator
@@ -0,0 +1 @@
+[General]
diff --git a/tests/genericprojectmanager/testdata_mixedproject2/mixedproject2.files b/tests/genericprojectmanager/testdata_mixedproject2/mixedproject2.files
new file mode 100644
index 0000000000000000000000000000000000000000..546405cf8c0269bb9cf421ddbee66ecd5e965b32
--- /dev/null
+++ b/tests/genericprojectmanager/testdata_mixedproject2/mixedproject2.files
@@ -0,0 +1,3 @@
+main.cpp
+header.hpp
+impl.c
diff --git a/tests/genericprojectmanager/testdata_mixedproject2/mixedproject2.includes b/tests/genericprojectmanager/testdata_mixedproject2/mixedproject2.includes
new file mode 100644
index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391