diff --git a/src/plugins/texteditor/generichighlighter/highlightersettingspage.cpp b/src/plugins/texteditor/generichighlighter/highlightersettingspage.cpp
index 4a34bd6b320b9dc7ade84f7f0669eb129a346588..ea904d7286e42703e39a76cd86d3b3dad126b62b 100644
--- a/src/plugins/texteditor/generichighlighter/highlightersettingspage.cpp
+++ b/src/plugins/texteditor/generichighlighter/highlightersettingspage.cpp
@@ -77,7 +77,7 @@ void HighlighterSettingsPage::HighlighterSettingsPagePrivate::ensureInitialized(
 
 HighlighterSettingsPage::HighlighterSettingsPage(Core::Id id, QObject *parent) :
     TextEditorOptionsPage(parent),
-    m_requestMimeTypeRegistration(false),
+    m_requestHighlightFileRegistration(false),
     m_d(new HighlighterSettingsPagePrivate(id))
 {
     setId(m_d->m_id);
@@ -122,9 +122,9 @@ void HighlighterSettingsPage::apply()
     if (settingsChanged())
         settingsFromUI();
 
-    if (m_requestMimeTypeRegistration) {
-        Manager::instance()->registerMimeTypes();
-        m_requestMimeTypeRegistration = false;
+    if (m_requestHighlightFileRegistration) {
+        Manager::instance()->registerHighlightingFiles();
+        m_requestHighlightFileRegistration = false;
     }
 }
 
@@ -146,12 +146,12 @@ const HighlighterSettings &HighlighterSettingsPage::highlighterSettings() const
 void HighlighterSettingsPage::settingsFromUI()
 {
     m_d->ensureInitialized();
-    if (!m_requestMimeTypeRegistration && (
+    if (!m_requestHighlightFileRegistration && (
         m_d->m_settings.definitionFilesPath() != m_d->m_page->definitionFilesPath->path() ||
         m_d->m_settings.fallbackDefinitionFilesPath() !=
             m_d->m_page->fallbackDefinitionFilesPath->path() ||
         m_d->m_settings.useFallbackLocation() != m_d->m_page->useFallbackLocation->isChecked())) {
-        m_requestMimeTypeRegistration = true;
+        m_requestHighlightFileRegistration = true;
     }
 
     m_d->m_settings.setDefinitionFilesPath(m_d->m_page->definitionFilesPath->path());
@@ -212,8 +212,8 @@ void HighlighterSettingsPage::manageDefinitions(const QList<DefinitionMetaDataPt
     ManageDefinitionsDialog dialog(metaData,
                                    m_d->m_page->definitionFilesPath->path() + QLatin1Char('/'),
                                    m_d->m_page->definitionFilesPath->buttonAtIndex(1)->window());
-    if (dialog.exec() && !m_requestMimeTypeRegistration)
-        m_requestMimeTypeRegistration = true;
+    if (dialog.exec() && !m_requestHighlightFileRegistration)
+        m_requestHighlightFileRegistration = true;
     setDownloadDefinitionsState(m_d->m_page->definitionFilesPath->isValid());
 }
 
diff --git a/src/plugins/texteditor/generichighlighter/highlightersettingspage.h b/src/plugins/texteditor/generichighlighter/highlightersettingspage.h
index f1bd8f6c4a26550cb3ce810a2de0b56a410b5c06..4c19e67fd05c43e7a7efdd46f21ccdb7ee0b463a 100644
--- a/src/plugins/texteditor/generichighlighter/highlightersettingspage.h
+++ b/src/plugins/texteditor/generichighlighter/highlightersettingspage.h
@@ -71,7 +71,7 @@ private:
 
     bool settingsChanged() const;
 
-    bool m_requestMimeTypeRegistration;
+    bool m_requestHighlightFileRegistration;
 
     struct HighlighterSettingsPagePrivate;
     HighlighterSettingsPagePrivate *m_d;
diff --git a/src/plugins/texteditor/generichighlighter/manager.cpp b/src/plugins/texteditor/generichighlighter/manager.cpp
index e7fdf65a34e7fbb343d983a7fbdd6da44da7f14c..08dc24856b50997bc1a34e2d4d11cc537a75c46d 100644
--- a/src/plugins/texteditor/generichighlighter/manager.cpp
+++ b/src/plugins/texteditor/generichighlighter/manager.cpp
@@ -115,7 +115,7 @@ Manager::Manager() :
     m_multiDownloader(0),
     m_hasQueuedRegistration(false)
 {
-    connect(&m_registeringWatcher, SIGNAL(finished()), this, SLOT(registerMimeTypesFinished()));
+    connect(&m_registeringWatcher, SIGNAL(finished()), this, SLOT(registerHighlightingFilesFinished()));
 }
 
 Manager::~Manager()
@@ -138,20 +138,68 @@ QString Manager::definitionIdByName(const QString &name) const
     return m_register.m_idByName.value(name);
 }
 
-QString Manager::definitionIdByMimeType(const QString &mimeType) const
+static bool matchesPattern(const QString &fileName, DefinitionMetaDataPtr metaData)
 {
-    return m_register.m_idByMimeType.value(mimeType);
+    if (metaData.isNull())
+        return false;
+    foreach (const QString &pattern, metaData->patterns) {
+        QRegExp reg(pattern, Qt::CaseSensitive, QRegExp::Wildcard);
+        if (reg.exactMatch(fileName))
+            return true;
+    }
+    return false;
 }
 
-QString Manager::definitionIdByAnyMimeType(const QStringList &mimeTypes) const
+QString Manager::definitionIdByMimeType(const Core::MimeType &mimeType) const
 {
-    QString definitionId;
-    foreach (const QString &mimeType, mimeTypes) {
-        definitionId = definitionIdByMimeType(mimeType);
-        if (!definitionId.isEmpty())
-            break;
+    QList<Core::MimeType> queue;
+    queue.append(mimeType);
+    while (!queue.isEmpty()) {
+        const Core::MimeType mt = queue.takeFirst();
+        const QString id = m_register.m_idByMimeType.value(mt.type());
+        if (!id.isEmpty())
+            return id;
+        foreach (const QString &parent, mt.subClassesOf()) {
+            const Core::MimeType parentMt = Core::MimeDatabase::findByType(parent);
+            if (!parentMt.isNull())
+                queue.append(parentMt);
+        }
     }
-    return definitionId;
+    return QString();
+}
+
+QString Manager::definitionIdByFile(const QString &filePath) const
+{
+    const QString fileName = QFileInfo(filePath).fileName();
+    // find best match
+    QString bestId;
+    int bestPriority = -1;
+    auto it = m_register.m_definitionsMetaData.constBegin();
+    while (it != m_register.m_definitionsMetaData.constEnd()) {
+        DefinitionMetaDataPtr metaData = it.value();
+        if (metaData->priority > bestPriority && matchesPattern(fileName, metaData)) {
+            bestId = metaData->id;
+            bestPriority = metaData->priority;
+        }
+        ++it;
+    }
+    return bestId;
+}
+
+QString Manager::definitionIdByMimeTypeAndFile(const MimeType &mimeType, const QString &filePath) const
+{
+    QString id = definitionIdByMimeType(mimeType);
+    if (!filePath.isEmpty()) {
+        QString idByFile;
+        const QString fileName = QFileInfo(filePath).fileName();
+        // if mime type check returned no result, or doesn't match the patterns,
+        // prefer a match by pattern
+        if (id.isEmpty() || !matchesPattern(fileName, m_register.m_definitionsMetaData.value(id)))
+            idByFile = definitionIdByFile(filePath);
+        if (!idByFile.isEmpty())
+            id = idByFile;
+    }
+    return id;
 }
 
 DefinitionMetaDataPtr Manager::availableDefinitionByName(const QString &name) const
@@ -206,51 +254,28 @@ class ManagerProcessor : public QObject
     Q_OBJECT
 public:
     ManagerProcessor();
-    void process(QFutureInterface<QPair<Manager::RegisterData,
-                                        QList<MimeType> > > &future);
+    void process(QFutureInterface<Manager::RegisterData> &future);
 
     QStringList m_definitionsPaths;
-    QSet<QString> m_knownMimeTypes;
-    QSet<QString> m_knownSuffixes;
-    QHash<QString, MimeType> m_userModified;
     static const int kMaxProgress;
 };
 
 const int ManagerProcessor::kMaxProgress = 200;
 
 ManagerProcessor::ManagerProcessor()
-    : m_knownSuffixes(QSet<QString>::fromList(MimeDatabase::suffixes()))
 {
     const HighlighterSettings &settings = TextEditorSettings::highlighterSettings();
     m_definitionsPaths.append(settings.definitionFilesPath());
     if (settings.useFallbackLocation())
         m_definitionsPaths.append(settings.fallbackDefinitionFilesPath());
-
-    foreach (const MimeType &userMimeType, MimeDatabase::readUserModifiedMimeTypes())
-        m_userModified.insert(userMimeType.type(), userMimeType);
-    foreach (const MimeType &mimeType, MimeDatabase::mimeTypes())
-        m_knownMimeTypes.insert(mimeType.type());
 }
 
-void ManagerProcessor::process(QFutureInterface<QPair<Manager::RegisterData,
-                                                      QList<MimeType> > > &future)
+void ManagerProcessor::process(QFutureInterface<Manager::RegisterData> &future)
 {
     future.setProgressRange(0, kMaxProgress);
 
-    // @TODO: Improve MIME database to handle the following limitation.
-    // The generic highlighter only register its types after all other plugins
-    // have populated Creator's MIME database (so it does not override anything).
-    // When the generic highlighter settings change only its internal data is cleaned-up
-    // and rebuilt. Creator's MIME database is not touched. So depending on how the
-    // user plays around with the generic highlighter file definitions (changing
-    // duplicated patterns, for example), some changes might not be reflected.
-    // A definitive implementation would require some kind of re-load or update
-    // (considering hierarchies, aliases, etc) of the MIME database whenever there
-    // is a change in the generic highlighter settings.
-
     Manager::RegisterData data;
-    QList<MimeType> newMimeTypes;
-
+    // iterate through paths in order, high priority > low priority
     foreach (const QString &path, m_definitionsPaths) {
         if (path.isEmpty())
             continue;
@@ -258,93 +283,47 @@ void ManagerProcessor::process(QFutureInterface<QPair<Manager::RegisterData,
         QDir definitionsDir(path);
         QStringList filter(QLatin1String("*.xml"));
         definitionsDir.setNameFilters(filter);
-        QList<DefinitionMetaDataPtr> allMetaData;
         foreach (const QFileInfo &fileInfo, definitionsDir.entryInfoList()) {
-            const DefinitionMetaDataPtr &metaData =
-                    Manager::parseMetadata(fileInfo);
-            if (!metaData.isNull())
-                allMetaData.append(metaData);
-        }
-
-        // Consider definitions with higher priority first.
-        Utils::sort(allMetaData, [](const DefinitionMetaDataPtr &l,
-                                    const DefinitionMetaDataPtr &r) {
-            return l->priority > r->priority;
-        });
-
-        foreach (const DefinitionMetaDataPtr &metaData, allMetaData) {
             if (future.isCanceled())
                 return;
             if (future.progressValue() < kMaxProgress - 1)
                 future.setProgressValue(future.progressValue() + 1);
 
-            if (data.m_idByName.contains(metaData->name))
-                // Name already exists... This is a fallback item, do not consider it.
-                continue;
-
-            const QString &id = metaData->id;
-            data.m_idByName.insert(metaData->name, id);
-            data.m_definitionsMetaData.insert(id, metaData);
-
-            static const QStringList textPlain(QLatin1String("text/plain"));
-
-            // A definition can specify multiple MIME types and file extensions/patterns,
-            // but all on a single string. So associate all patterns with all MIME types.
-            QList<MimeGlobPattern> globPatterns;
-            foreach (const QString &type, metaData->mimeTypes) {
-                if (data.m_idByMimeType.contains(type))
-                    continue;
-
-                data.m_idByMimeType.insert(type, id);
-                if (!m_knownMimeTypes.contains(type)) {
-                    m_knownMimeTypes.insert(type);
-
-                    MimeType mimeType;
-                    mimeType.setType(type);
-                    mimeType.setSubClassesOf(textPlain);
-                    mimeType.setComment(metaData->name);
-
-                    // If there's a user modification for this mime type, we want to use the
-                    // modified patterns and rule-based matchers. If not, just consider what
-                    // is specified in the definition file.
-                    QHash<QString, MimeType>::const_iterator it =
-                        m_userModified.find(mimeType.type());
-                    if (it == m_userModified.end()) {
-                        if (globPatterns.isEmpty()) {
-                            foreach (const QString &pattern, metaData->patterns) {
-                                static const QLatin1String mark("*.");
-                                if (pattern.startsWith(mark)) {
-                                    const QString &suffix = pattern.right(pattern.length() - 2);
-                                    if (!m_knownSuffixes.contains(suffix))
-                                        m_knownSuffixes.insert(suffix);
-                                    else
-                                        continue;
-                                }
-                                globPatterns.append(MimeGlobPattern(pattern, 50));
-                            }
-                        }
-                        mimeType.setGlobPatterns(globPatterns);
-                    } else {
-                        mimeType.setGlobPatterns(it.value().globPatterns());
-                        mimeType.setMagicRuleMatchers(it.value().magicRuleMatchers());
+            const DefinitionMetaDataPtr &metaData =
+                    Manager::parseMetadata(fileInfo);
+            // skip failing or already existing definitions
+            if (!metaData.isNull() && !data.m_idByName.contains(metaData->name)) {
+                const QString id = metaData->id;
+                data.m_idByName.insert(metaData->name, id);
+                data.m_definitionsMetaData.insert(id, metaData);
+                foreach (const QString &mt, metaData->mimeTypes) {
+                    bool insert = true;
+                    // check if there is already a definition registered with higher priority
+                    const QString existingDefinition = data.m_idByMimeType.value(mt);
+                    if (!existingDefinition.isEmpty()) {
+                        // check priorities
+                        DefinitionMetaDataPtr existingMetaData =
+                                data.m_definitionsMetaData.value(existingDefinition);
+                        if (!existingMetaData.isNull() && existingMetaData->priority > metaData->priority)
+                            insert = false;
                     }
-
-                    newMimeTypes.append(mimeType);
+                    if (insert)
+                        data.m_idByMimeType.insert(mt, id);
                 }
             }
         }
     }
 
-    future.reportResult(qMakePair(data, newMimeTypes));
+    future.reportResult(data);
 }
 
-void Manager::registerMimeTypes()
+void Manager::registerHighlightingFiles()
 {
     if (!m_registeringWatcher.isRunning()) {
         clear();
 
         ManagerProcessor *processor = new ManagerProcessor;
-        QFuture<QPair<RegisterData, QList<MimeType> > > future =
+        QFuture<RegisterData> future =
             QtConcurrent::run(&ManagerProcessor::process, processor);
         connect(&m_registeringWatcher, SIGNAL(finished()), processor, SLOT(deleteLater()));
         m_registeringWatcher.setFuture(future);
@@ -354,29 +333,22 @@ void Manager::registerMimeTypes()
     }
 }
 
-void Manager::registerMimeTypesFinished()
+void Manager::registerHighlightingFilesFinished()
 {
     if (m_hasQueuedRegistration) {
         m_hasQueuedRegistration = false;
-        registerMimeTypes();
+        registerHighlightingFiles();
     } else if (!m_registeringWatcher.isCanceled()) {
-        const QPair<RegisterData, QList<MimeType> > &result = m_registeringWatcher.result();
-        m_register = result.first;
+        m_register = m_registeringWatcher.result();
 
-        foreach (const MimeType &mimeType, result.second)
-            MimeDatabase::addMimeType(mimeType);
-
-        emit mimeTypesRegistered();
+        emit highlightingFilesRegistered();
     }
 }
 
 DefinitionMetaDataPtr Manager::parseMetadata(const QFileInfo &fileInfo)
 {
     static const QLatin1Char kSemiColon(';');
-    static const QLatin1Char kSpace(' ');
-    static const QLatin1Char kDash('-');
     static const QLatin1String kLanguage("language");
-    static const QLatin1String kArtificial("text/x-artificial-");
 
     QFile definitionFile(fileInfo.absoluteFilePath());
     if (!definitionFile.open(QIODevice::ReadOnly | QIODevice::Text))
@@ -397,17 +369,8 @@ DefinitionMetaDataPtr Manager::parseMetadata(const QFileInfo &fileInfo)
             metaData->patterns = atts.value(QLatin1String(kExtensions))
                                   .toString().split(kSemiColon, QString::SkipEmptyParts);
 
-            QStringList mimeTypes = atts.value(QLatin1String(kMimeType)).
+            metaData->mimeTypes = atts.value(QLatin1String(kMimeType)).
                                     toString().split(kSemiColon, QString::SkipEmptyParts);
-            if (mimeTypes.isEmpty()) {
-                // There are definitions which do not specify a MIME type, but specify file
-                // patterns. Creating an artificial MIME type is a workaround.
-                QString artificialType(kArtificial);
-                artificialType.append(metaData->name.trimmed().replace(kSpace, kDash));
-                mimeTypes.append(artificialType);
-            }
-            metaData->mimeTypes = mimeTypes;
-
             break;
         }
     }
diff --git a/src/plugins/texteditor/generichighlighter/manager.h b/src/plugins/texteditor/generichighlighter/manager.h
index 0b8bf4dca94438e7e6a73dad3a77f928ebc5520b..4105f65b64610a06c9cc111ad9cef3e2edac64de 100644
--- a/src/plugins/texteditor/generichighlighter/manager.h
+++ b/src/plugins/texteditor/generichighlighter/manager.h
@@ -69,8 +69,10 @@ public:
     static Manager *instance();
 
     QString definitionIdByName(const QString &name) const;
-    QString definitionIdByMimeType(const QString &mimeType) const;
-    QString definitionIdByAnyMimeType(const QStringList &mimeTypes) const;
+    QString definitionIdByMimeType(const Core::MimeType &mimeType) const;
+    QString definitionIdByFile(const QString &filePath) const;
+    QString definitionIdByMimeTypeAndFile(const Core::MimeType &mimeType,
+                                          const QString &filePath) const;
     DefinitionMetaDataPtr availableDefinitionByName(const QString &name) const;
 
     bool isBuildingDefinition(const QString &id) const;
@@ -84,15 +86,15 @@ public:
     static DefinitionMetaDataPtr parseMetadata(const QFileInfo &fileInfo);
 
 public slots:
-    void registerMimeTypes();
+    void registerHighlightingFiles();
 
 private slots:
-    void registerMimeTypesFinished();
+    void registerHighlightingFilesFinished();
     void downloadAvailableDefinitionsListFinished();
     void downloadDefinitionsFinished();
 
 signals:
-    void mimeTypesRegistered();
+    void highlightingFilesRegistered();
 
 private:
     Manager();
@@ -114,7 +116,7 @@ private:
     };
     RegisterData m_register;
     bool m_hasQueuedRegistration;
-    QFutureWatcher<QPair<RegisterData, QList<Core::MimeType> > > m_registeringWatcher;
+    QFutureWatcher<RegisterData> m_registeringWatcher;
     friend class ManagerProcessor;
 
 signals:
diff --git a/src/plugins/texteditor/highlighterutils.cpp b/src/plugins/texteditor/highlighterutils.cpp
index 0e84c347e73ad5ce37c51f2cc383d41ef0462b4b..2c0dc7b6faa83ee4aafea0104c8b9233c1320ae8 100644
--- a/src/plugins/texteditor/highlighterutils.cpp
+++ b/src/plugins/texteditor/highlighterutils.cpp
@@ -37,30 +37,10 @@
 using namespace TextEditor;
 using namespace Internal;
 
-QString TextEditor::findDefinitionId(const Core::MimeType &mimeType,
-                         bool considerParents)
-{
-    QString definitionId = Manager::instance()->definitionIdByAnyMimeType(mimeType.aliases());
-    if (definitionId.isEmpty() && considerParents) {
-        definitionId = Manager::instance()->definitionIdByAnyMimeType(mimeType.subClassesOf());
-        if (definitionId.isEmpty()) {
-            foreach (const QString &parent, mimeType.subClassesOf()) {
-                const Core::MimeType &parentMimeType = Core::MimeDatabase::findByType(parent);
-                definitionId = findDefinitionId(parentMimeType, considerParents);
-            }
-        }
-    }
-    return definitionId;
-}
-
 void TextEditor::setMimeTypeForHighlighter(Highlighter *highlighter, const Core::MimeType &mimeType,
-                                           QString *foundDefinitionId)
+                                           const QString &filePath, QString *foundDefinitionId)
 {
-    const QString type = mimeType.type();
-    QString definitionId = Manager::instance()->definitionIdByMimeType(type);
-    if (definitionId.isEmpty())
-        definitionId = findDefinitionId(mimeType, true);
-
+    QString definitionId = Manager::instance()->definitionIdByMimeTypeAndFile(mimeType, filePath);
     if (!definitionId.isEmpty()) {
         const QSharedPointer<HighlightDefinition> &definition =
             Manager::instance()->definition(definitionId);
@@ -72,9 +52,3 @@ void TextEditor::setMimeTypeForHighlighter(Highlighter *highlighter, const Core:
         *foundDefinitionId = definitionId;
 }
 
-SyntaxHighlighter *TextEditor::createGenericSyntaxHighlighter(const Core::MimeType &mimeType)
-{
-    Highlighter *highlighter = new Highlighter();
-    setMimeTypeForHighlighter(highlighter, mimeType);
-    return highlighter;
-}
diff --git a/src/plugins/texteditor/highlighterutils.h b/src/plugins/texteditor/highlighterutils.h
index b0e1b70b699f5ffe092197a02663d7c652960266..0d9a9b09423a7636466190ed8ef075a25979d4e5 100644
--- a/src/plugins/texteditor/highlighterutils.h
+++ b/src/plugins/texteditor/highlighterutils.h
@@ -43,12 +43,10 @@ namespace Core { class MimeType; }
 namespace TextEditor {
 
 class Highlighter;
-class SyntaxHighlighter;
 
 void setMimeTypeForHighlighter(Highlighter *highlighter, const Core::MimeType &mimeType,
+                               const QString &filePath,
                                QString *foundDefinitionId = 0);
-QString findDefinitionId(const Core::MimeType &mimeType, bool considerParents);
-TEXTEDITOR_EXPORT SyntaxHighlighter *createGenericSyntaxHighlighter(const Core::MimeType &mimeType);
 
 } // namespace TextEditor
 
diff --git a/src/plugins/texteditor/texteditor.cpp b/src/plugins/texteditor/texteditor.cpp
index c9c824f19a0a35b846dfa8f415e4c3fb18598776..56adaf2829fc365ddb7994599cf3447780fb421a 100644
--- a/src/plugins/texteditor/texteditor.cpp
+++ b/src/plugins/texteditor/texteditor.cpp
@@ -7178,7 +7178,8 @@ void TextEditorWidget::configureGenericHighlighter()
         d->m_isMissingSyntaxDefinition = true;
 
         QString definitionId;
-        setMimeTypeForHighlighter(highlighter, mimeType, &definitionId);
+        setMimeTypeForHighlighter(highlighter, mimeType, textDocument()->filePath().toString(),
+                                  &definitionId);
 
         if (!definitionId.isEmpty()) {
             d->m_isMissingSyntaxDefinition = false;
@@ -7218,7 +7219,7 @@ void TextEditorWidget::setupGenericHighlighter()
     connect(textDocument(), &IDocument::filePathChanged,
             d, &TextEditorWidgetPrivate::reconfigure);
 
-    connect(Manager::instance(), &Manager::mimeTypesRegistered,
+    connect(Manager::instance(), &Manager::highlightingFilesRegistered,
             d, &TextEditorWidgetPrivate::reconfigure);
 
     updateEditorInfoBar(this);
diff --git a/src/plugins/texteditor/texteditorplugin.cpp b/src/plugins/texteditor/texteditorplugin.cpp
index 0d3b11e1440562fbdd6bb0babe67db1608847f35..efa8d8b4bdc419f0412e845acf49b750c5aa150d 100644
--- a/src/plugins/texteditor/texteditorplugin.cpp
+++ b/src/plugins/texteditor/texteditorplugin.cpp
@@ -125,7 +125,7 @@ bool TextEditorPlugin::initialize(const QStringList &arguments, QString *errorMe
     });
 
     // Generic highlighter.
-    connect(ICore::instance(), &ICore::coreOpened, Manager::instance(), &Manager::registerMimeTypes);
+    connect(ICore::instance(), &ICore::coreOpened, Manager::instance(), &Manager::registerHighlightingFiles);
 
     // Add text snippet provider.
     addAutoReleasedObject(new PlainTextSnippetProvider);