diff options
Diffstat (limited to 'src/tools/moc')
-rw-r--r-- | src/tools/moc/generator.cpp | 340 | ||||
-rw-r--r-- | src/tools/moc/preprocessor.cpp | 59 | ||||
-rw-r--r-- | src/tools/moc/preprocessor.h | 4 |
3 files changed, 247 insertions, 156 deletions
diff --git a/src/tools/moc/generator.cpp b/src/tools/moc/generator.cpp index 6c5e772e8c..fcc43aca68 100644 --- a/src/tools/moc/generator.cpp +++ b/src/tools/moc/generator.cpp @@ -230,13 +230,23 @@ void Generator::generateCode() // // Build stringdata struct // + const int constCharArraySizeLimit = 65535; fprintf(out, "struct qt_meta_stringdata_%s_t {\n", qualifiedClassNameIdentifier.constData()); fprintf(out, " QByteArrayData data[%d];\n", strings.size()); { - int len = 0; - for (int i = 0; i < strings.size(); ++i) - len += strings.at(i).length() + 1; - fprintf(out, " char stringdata[%d];\n", len); + int stringDataLength = 0; + int stringDataCounter = 0; + for (int i = 0; i < strings.size(); ++i) { + int thisLength = strings.at(i).length() + 1; + stringDataLength += thisLength; + if (stringDataLength / constCharArraySizeLimit) { + // save previous stringdata and start computing the next one. + fprintf(out, " char stringdata%d[%d];\n", stringDataCounter++, stringDataLength - thisLength); + stringDataLength = thisLength; + } + } + fprintf(out, " char stringdata%d[%d];\n", stringDataCounter, stringDataLength); + } fprintf(out, "};\n"); @@ -247,7 +257,7 @@ void Generator::generateCode() // QByteArrayData::data() implementation returning simply "this + offset". fprintf(out, "#define QT_MOC_LITERAL(idx, ofs, len) \\\n" " Q_STATIC_BYTE_ARRAY_DATA_HEADER_INITIALIZER_WITH_OFFSET(len, \\\n" - " qptrdiff(offsetof(qt_meta_stringdata_%s_t, stringdata) + ofs \\\n" + " qptrdiff(offsetof(qt_meta_stringdata_%s_t, stringdata0) + ofs \\\n" " - idx * sizeof(QByteArrayData)) \\\n" " )\n", qualifiedClassNameIdentifier.constData()); @@ -282,9 +292,18 @@ void Generator::generateCode() fprintf(out, " \""); int col = 0; int len = 0; + int stringDataLength = 0; for (int i = 0; i < strings.size(); ++i) { QByteArray s = strings.at(i); len = s.length(); + stringDataLength += len + 1; + if (stringDataLength >= constCharArraySizeLimit) { + fprintf(out, "\",\n \""); + stringDataLength = len + 1; + col = 0; + } else if (i) + fputs("\\0", out); // add \0 at the end of each string + if (col && col + len >= 72) { fprintf(out, "\"\n \""); col = 0; @@ -309,9 +328,6 @@ void Generator::generateCode() idx += spanLen; col += spanLen; } - - if (i != strings.size() - 1) // skip the last \0 the c++ will add it for us - fputs("\\0", out); col += len + 2; } @@ -359,7 +375,13 @@ void Generator::generateCode() fprintf(out, " %4d, %4d, // constructors\n", isConstructible ? cdef->constructorList.count() : 0, isConstructible ? index : 0); - fprintf(out, " %4d, // flags\n", 0); + int flags = 0; + if (cdef->hasQGadget) { + // Ideally, all the classes could have that flag. But this broke classes generated + // by qdbusxml2cpp which generate code that require that we call qt_metacall for properties + flags |= PropertyAccessInStaticMetaCall; + } + fprintf(out, " %4d, // flags\n", flags); fprintf(out, " %4d, // signalCount\n", cdef->signalList.count()); @@ -425,7 +447,9 @@ void Generator::generateCode() // // Generate internal qt_static_metacall() function // - if (cdef->hasQObject && !isQt) + const bool hasStaticMetaCall = !isQt && + (cdef->hasQObject || !cdef->methodList.isEmpty() || !cdef->propertyList.isEmpty()); + if (hasStaticMetaCall) generateStaticMetacall(); // @@ -513,7 +537,7 @@ void Generator::generateCode() fprintf(out, "qt_meta_stringdata_%s.data,\n" " qt_meta_data_%s, ", qualifiedClassNameIdentifier.constData(), qualifiedClassNameIdentifier.constData()); - if (cdef->hasQObject && !isQt) + if (hasStaticMetaCall) fprintf(out, " qt_static_metacall, "); else fprintf(out, " Q_NULLPTR, "); @@ -538,7 +562,7 @@ void Generator::generateCode() // fprintf(out, "\nvoid *%s::qt_metacast(const char *_clname)\n{\n", cdef->qualified.constData()); fprintf(out, " if (!_clname) return Q_NULLPTR;\n"); - fprintf(out, " if (!strcmp(_clname, qt_meta_stringdata_%s.stringdata))\n" + fprintf(out, " if (!strcmp(_clname, qt_meta_stringdata_%s.stringdata0))\n" " return static_cast<void*>(const_cast< %s*>(this));\n", qualifiedClassNameIdentifier.constData(), cdef->classname.constData()); for (int i = 1; i < cdef->superclassList.size(); ++i) { // for all superclasses but the first one @@ -919,10 +943,6 @@ void Generator::generateMetacall() } if (cdef->propertyList.size()) { - bool needGet = false; - bool needTempVarForGet = false; - bool needSet = false; - bool needReset = false; bool needDesignable = false; bool needScriptable = false; bool needStored = false; @@ -930,132 +950,21 @@ void Generator::generateMetacall() bool needUser = false; for (int i = 0; i < cdef->propertyList.size(); ++i) { const PropertyDef &p = cdef->propertyList.at(i); - needGet |= !p.read.isEmpty() || !p.member.isEmpty(); - if (!p.read.isEmpty() || !p.member.isEmpty()) - needTempVarForGet |= (p.gspec != PropertyDef::PointerSpec - && p.gspec != PropertyDef::ReferenceSpec); - - needSet |= !p.write.isEmpty() || (!p.member.isEmpty() && !p.constant); - needReset |= !p.reset.isEmpty(); needDesignable |= p.designable.endsWith(')'); needScriptable |= p.scriptable.endsWith(')'); needStored |= p.stored.endsWith(')'); needEditable |= p.editable.endsWith(')'); needUser |= p.user.endsWith(')'); } - fprintf(out, "\n#ifndef QT_NO_PROPERTIES\n "); + fprintf(out, "\n#ifndef QT_NO_PROPERTIES\n "); if (needElse) - fprintf(out, " else "); - fprintf(out, "if (_c == QMetaObject::ReadProperty) {\n"); - if (needGet) { - if (needTempVarForGet) - fprintf(out, " void *_v = _a[0];\n"); - fprintf(out, " switch (_id) {\n"); - for (int propindex = 0; propindex < cdef->propertyList.size(); ++propindex) { - const PropertyDef &p = cdef->propertyList.at(propindex); - if (p.read.isEmpty() && p.member.isEmpty()) - continue; - QByteArray prefix; - if (p.inPrivateClass.size()) { - prefix = p.inPrivateClass; - prefix.append("->"); - } - if (p.gspec == PropertyDef::PointerSpec) - fprintf(out, " case %d: _a[0] = const_cast<void*>(reinterpret_cast<const void*>(%s%s())); break;\n", - propindex, prefix.constData(), p.read.constData()); - else if (p.gspec == PropertyDef::ReferenceSpec) - fprintf(out, " case %d: _a[0] = const_cast<void*>(reinterpret_cast<const void*>(&%s%s())); break;\n", - propindex, prefix.constData(), p.read.constData()); - else if (cdef->enumDeclarations.value(p.type, false)) - fprintf(out, " case %d: *reinterpret_cast<int*>(_v) = QFlag(%s%s()); break;\n", - propindex, prefix.constData(), p.read.constData()); - else if (!p.read.isEmpty()) - fprintf(out, " case %d: *reinterpret_cast< %s*>(_v) = %s%s(); break;\n", - propindex, p.type.constData(), prefix.constData(), p.read.constData()); - else - fprintf(out, " case %d: *reinterpret_cast< %s*>(_v) = %s%s; break;\n", - propindex, p.type.constData(), prefix.constData(), p.member.constData()); - } - fprintf(out, " default: break;\n"); - fprintf(out, " }\n"); - } - - fprintf(out, - " _id -= %d;\n" - " }", cdef->propertyList.count()); - - fprintf(out, " else "); - fprintf(out, "if (_c == QMetaObject::WriteProperty) {\n"); - - if (needSet) { - fprintf(out, " void *_v = _a[0];\n"); - fprintf(out, " switch (_id) {\n"); - for (int propindex = 0; propindex < cdef->propertyList.size(); ++propindex) { - const PropertyDef &p = cdef->propertyList.at(propindex); - if (p.constant) - continue; - if (p.write.isEmpty() && p.member.isEmpty()) - continue; - QByteArray prefix; - if (p.inPrivateClass.size()) { - prefix = p.inPrivateClass; - prefix.append("->"); - } - if (cdef->enumDeclarations.value(p.type, false)) { - fprintf(out, " case %d: %s%s(QFlag(*reinterpret_cast<int*>(_v))); break;\n", - propindex, prefix.constData(), p.write.constData()); - } else if (!p.write.isEmpty()) { - fprintf(out, " case %d: %s%s(*reinterpret_cast< %s*>(_v)); break;\n", - propindex, prefix.constData(), p.write.constData(), p.type.constData()); - } else { - fprintf(out, " case %d:\n", propindex); - fprintf(out, " if (%s%s != *reinterpret_cast< %s*>(_v)) {\n", - prefix.constData(), p.member.constData(), p.type.constData()); - fprintf(out, " %s%s = *reinterpret_cast< %s*>(_v);\n", - prefix.constData(), p.member.constData(), p.type.constData()); - if (!p.notify.isEmpty() && p.notifyId != -1) { - const FunctionDef &f = cdef->signalList.at(p.notifyId); - if (f.arguments.size() == 0) - fprintf(out, " Q_EMIT %s();\n", p.notify.constData()); - else if (f.arguments.size() == 1 && f.arguments.at(0).normalizedType == p.type) - fprintf(out, " Q_EMIT %s(%s%s);\n", - p.notify.constData(), prefix.constData(), p.member.constData()); - } - fprintf(out, " }\n"); - fprintf(out, " break;\n"); - } - } - fprintf(out, " default: break;\n"); - fprintf(out, " }\n"); - } - + fprintf(out, "else "); fprintf(out, - " _id -= %d;\n" - " }", cdef->propertyList.count()); - - fprintf(out, " else "); - fprintf(out, "if (_c == QMetaObject::ResetProperty) {\n"); - if (needReset) { - fprintf(out, " switch (_id) {\n"); - for (int propindex = 0; propindex < cdef->propertyList.size(); ++propindex) { - const PropertyDef &p = cdef->propertyList.at(propindex); - if (!p.reset.endsWith(')')) - continue; - QByteArray prefix; - if (p.inPrivateClass.size()) { - prefix = p.inPrivateClass; - prefix.append("->"); - } - fprintf(out, " case %d: %s%s; break;\n", - propindex, prefix.constData(), p.reset.constData()); - } - fprintf(out, " default: break;\n"); - fprintf(out, " }\n"); - } - fprintf(out, - " _id -= %d;\n" - " }", cdef->propertyList.count()); + "if (_c == QMetaObject::ReadProperty || _c == QMetaObject::WriteProperty\n" + " || _c == QMetaObject::ResetProperty || _c == QMetaObject::RegisterPropertyMetaType) {\n" + " qt_static_metacall(this, _c, _id, _a);\n" + " _id -= %d;\n }", cdef->propertyList.count()); fprintf(out, " else "); fprintf(out, "if (_c == QMetaObject::QueryPropertyDesignable) {\n"); @@ -1153,16 +1062,6 @@ void Generator::generateMetacall() " _id -= %d;\n" " }", cdef->propertyList.count()); - fprintf(out, " else "); - fprintf(out, "if (_c == QMetaObject::RegisterPropertyMetaType) {\n"); - fprintf(out, " if (_id < %d)\n", cdef->propertyList.size()); - - if (automaticPropertyMetaTypesHelper().isEmpty()) - fprintf(out, " *reinterpret_cast<int*>(_a[0]) = -1;\n"); - else - fprintf(out, " qt_static_metacall(this, _c, _id, _a);\n"); - fprintf(out, " _id -= %d;\n }", cdef->propertyList.size()); - fprintf(out, "\n#endif // QT_NO_PROPERTIES"); } if (methodList.size() || cdef->signalList.size() || cdef->propertyList.size()) @@ -1246,10 +1145,14 @@ void Generator::generateStaticMetacall() else fprintf(out, " "); fprintf(out, "if (_c == QMetaObject::InvokeMetaMethod) {\n"); + if (cdef->hasQObject) { #ifndef QT_NO_DEBUG - fprintf(out, " Q_ASSERT(staticMetaObject.cast(_o));\n"); + fprintf(out, " Q_ASSERT(staticMetaObject.cast(_o));\n"); #endif - fprintf(out, " %s *_t = static_cast<%s *>(_o);\n", cdef->classname.constData(), cdef->classname.constData()); + fprintf(out, " %s *_t = static_cast<%s *>(_o);\n", cdef->classname.constData(), cdef->classname.constData()); + } else { + fprintf(out, " %s *_t = reinterpret_cast<%s *>(_o);\n", cdef->classname.constData(), cdef->classname.constData()); + } fprintf(out, " switch (_id) {\n"); for (int methodindex = 0; methodindex < methodList.size(); ++methodindex) { const FunctionDef &f = methodList.at(methodindex); @@ -1377,6 +1280,153 @@ void Generator::generateStaticMetacall() needElse = true; } + if (!cdef->propertyList.empty()) { + bool needGet = false; + bool needTempVarForGet = false; + bool needSet = false; + bool needReset = false; + for (int i = 0; i < cdef->propertyList.size(); ++i) { + const PropertyDef &p = cdef->propertyList.at(i); + needGet |= !p.read.isEmpty() || !p.member.isEmpty(); + if (!p.read.isEmpty() || !p.member.isEmpty()) + needTempVarForGet |= (p.gspec != PropertyDef::PointerSpec + && p.gspec != PropertyDef::ReferenceSpec); + + needSet |= !p.write.isEmpty() || (!p.member.isEmpty() && !p.constant); + needReset |= !p.reset.isEmpty(); + } + fprintf(out, "\n#ifndef QT_NO_PROPERTIES\n "); + + if (needElse) + fprintf(out, "else "); + fprintf(out, "if (_c == QMetaObject::ReadProperty) {\n"); + if (needGet) { + if (cdef->hasQObject) { +#ifndef QT_NO_DEBUG + fprintf(out, " Q_ASSERT(staticMetaObject.cast(_o));\n"); +#endif + fprintf(out, " %s *_t = static_cast<%s *>(_o);\n", cdef->classname.constData(), cdef->classname.constData()); + } else { + fprintf(out, " %s *_t = reinterpret_cast<%s *>(_o);\n", cdef->classname.constData(), cdef->classname.constData()); + } + if (needTempVarForGet) + fprintf(out, " void *_v = _a[0];\n"); + fprintf(out, " switch (_id) {\n"); + for (int propindex = 0; propindex < cdef->propertyList.size(); ++propindex) { + const PropertyDef &p = cdef->propertyList.at(propindex); + if (p.read.isEmpty() && p.member.isEmpty()) + continue; + QByteArray prefix = "_t->"; + if (p.inPrivateClass.size()) { + prefix += p.inPrivateClass + "->"; + } + if (p.gspec == PropertyDef::PointerSpec) + fprintf(out, " case %d: _a[0] = const_cast<void*>(reinterpret_cast<const void*>(%s%s())); break;\n", + propindex, prefix.constData(), p.read.constData()); + else if (p.gspec == PropertyDef::ReferenceSpec) + fprintf(out, " case %d: _a[0] = const_cast<void*>(reinterpret_cast<const void*>(&%s%s())); break;\n", + propindex, prefix.constData(), p.read.constData()); + else if (cdef->enumDeclarations.value(p.type, false)) + fprintf(out, " case %d: *reinterpret_cast<int*>(_v) = QFlag(%s%s()); break;\n", + propindex, prefix.constData(), p.read.constData()); + else if (!p.read.isEmpty()) + fprintf(out, " case %d: *reinterpret_cast< %s*>(_v) = %s%s(); break;\n", + propindex, p.type.constData(), prefix.constData(), p.read.constData()); + else + fprintf(out, " case %d: *reinterpret_cast< %s*>(_v) = %s%s; break;\n", + propindex, p.type.constData(), prefix.constData(), p.member.constData()); + } + fprintf(out, " default: break;\n"); + fprintf(out, " }\n"); + } + + fprintf(out, " }"); + + fprintf(out, " else "); + fprintf(out, "if (_c == QMetaObject::WriteProperty) {\n"); + + if (needSet) { + if (cdef->hasQObject) { +#ifndef QT_NO_DEBUG + fprintf(out, " Q_ASSERT(staticMetaObject.cast(_o));\n"); +#endif + fprintf(out, " %s *_t = static_cast<%s *>(_o);\n", cdef->classname.constData(), cdef->classname.constData()); + } else { + fprintf(out, " %s *_t = reinterpret_cast<%s *>(_o);\n", cdef->classname.constData(), cdef->classname.constData()); + } + fprintf(out, " void *_v = _a[0];\n"); + fprintf(out, " switch (_id) {\n"); + for (int propindex = 0; propindex < cdef->propertyList.size(); ++propindex) { + const PropertyDef &p = cdef->propertyList.at(propindex); + if (p.constant) + continue; + if (p.write.isEmpty() && p.member.isEmpty()) + continue; + QByteArray prefix = "_t->"; + if (p.inPrivateClass.size()) { + prefix += p.inPrivateClass + "->"; + } + if (cdef->enumDeclarations.value(p.type, false)) { + fprintf(out, " case %d: %s%s(QFlag(*reinterpret_cast<int*>(_v))); break;\n", + propindex, prefix.constData(), p.write.constData()); + } else if (!p.write.isEmpty()) { + fprintf(out, " case %d: %s%s(*reinterpret_cast< %s*>(_v)); break;\n", + propindex, prefix.constData(), p.write.constData(), p.type.constData()); + } else { + fprintf(out, " case %d:\n", propindex); + fprintf(out, " if (%s%s != *reinterpret_cast< %s*>(_v)) {\n", + prefix.constData(), p.member.constData(), p.type.constData()); + fprintf(out, " %s%s = *reinterpret_cast< %s*>(_v);\n", + prefix.constData(), p.member.constData(), p.type.constData()); + if (!p.notify.isEmpty() && p.notifyId != -1) { + const FunctionDef &f = cdef->signalList.at(p.notifyId); + if (f.arguments.size() == 0) + fprintf(out, " Q_EMIT _t->%s();\n", p.notify.constData()); + else if (f.arguments.size() == 1 && f.arguments.at(0).normalizedType == p.type) + fprintf(out, " Q_EMIT _t->%s(%s%s);\n", + p.notify.constData(), prefix.constData(), p.member.constData()); + } + fprintf(out, " }\n"); + fprintf(out, " break;\n"); + } + } + fprintf(out, " default: break;\n"); + fprintf(out, " }\n"); + } + + fprintf(out, " }"); + + fprintf(out, " else "); + fprintf(out, "if (_c == QMetaObject::ResetProperty) {\n"); + if (needReset) { + if (cdef->hasQObject) { +#ifndef QT_NO_DEBUG + fprintf(out, " Q_ASSERT(staticMetaObject.cast(_o));\n"); +#endif + fprintf(out, " %s *_t = static_cast<%s *>(_o);\n", cdef->classname.constData(), cdef->classname.constData()); + } else { + fprintf(out, " %s *_t = reinterpret_cast<%s *>(_o);\n", cdef->classname.constData(), cdef->classname.constData()); + } + fprintf(out, " switch (_id) {\n"); + for (int propindex = 0; propindex < cdef->propertyList.size(); ++propindex) { + const PropertyDef &p = cdef->propertyList.at(propindex); + if (!p.reset.endsWith(')')) + continue; + QByteArray prefix = "_t->"; + if (p.inPrivateClass.size()) { + prefix += p.inPrivateClass + "->"; + } + fprintf(out, " case %d: %s%s; break;\n", + propindex, prefix.constData(), p.reset.constData()); + } + fprintf(out, " default: break;\n"); + fprintf(out, " }\n"); + } + fprintf(out, " }"); + fprintf(out, "\n#endif // QT_NO_PROPERTIES"); + needElse = true; + } + if (needElse) fprintf(out, "\n"); diff --git a/src/tools/moc/preprocessor.cpp b/src/tools/moc/preprocessor.cpp index c5d6b58412..687c4f8474 100644 --- a/src/tools/moc/preprocessor.cpp +++ b/src/tools/moc/preprocessor.cpp @@ -52,11 +52,12 @@ static QByteArray cleaned(const QByteArray &input) QByteArray result; result.reserve(input.size()); const char *data = input.constData(); + const char *end = input.constData() + input.size(); char *output = result.data(); int newlines = 0; - while (*data) { - while (*data && is_space(*data)) + while (data != end) { + while (data != end && is_space(*data)) ++data; bool takeLine = (*data == '#'); if (*data == '%' && *(data+1) == ':') { @@ -66,15 +67,15 @@ static QByteArray cleaned(const QByteArray &input) if (takeLine) { *output = '#'; ++output; - do ++data; while (*data && is_space(*data)); + do ++data; while (data != end && is_space(*data)); } - while (*data) { + while (data != end) { // handle \\\n, \\\r\n and \\\r if (*data == '\\') { if (*(data + 1) == '\r') { ++data; } - if (*data && (*(data + 1) == '\n' || (*data) == '\r')) { + if (data != end && (*(data + 1) == '\n' || (*data) == '\r')) { ++newlines; data += 1; if (*data != '\r') @@ -201,7 +202,7 @@ Symbols Preprocessor::tokenize(const QByteArray& input, int lineNum, Preprocesso data = skipQuote(data); token = STRING_LITERAL; // concatenate multi-line strings for easier - // STRING_LITERAAL handling in moc + // STRING_LITERAL handling in moc if (!Preprocessor::preprocessOnly && !symbols.isEmpty() && symbols.last().token == STRING_LITERAL) { @@ -964,6 +965,43 @@ int Preprocessor::evaluateCondition() return expression.value(); } +static QByteArray readOrMapFile(QFile *file) +{ + const qint64 size = file->size(); + char *rawInput = reinterpret_cast<char*>(file->map(0, size)); + return rawInput ? QByteArray::fromRawData(rawInput, size) : file->readAll(); +} + +static void mergeStringLiterals(Symbols *_symbols) +{ + Symbols &symbols = *_symbols; + for (Symbols::iterator i = symbols.begin(); i != symbols.end(); ++i) { + if (i->token == STRING_LITERAL) { + Symbols::Iterator mergeSymbol = i; + int literalsLength = mergeSymbol->len; + while (++i != symbols.end() && i->token == STRING_LITERAL) + literalsLength += i->len - 2; // no quotes + + if (literalsLength != mergeSymbol->len) { + QByteArray mergeSymbolOriginalLexem = mergeSymbol->unquotedLexem(); + QByteArray &mergeSymbolLexem = mergeSymbol->lex; + mergeSymbolLexem.resize(0); + mergeSymbolLexem.reserve(literalsLength); + mergeSymbolLexem.append('"'); + mergeSymbolLexem.append(mergeSymbolOriginalLexem); + for (Symbols::const_iterator j = mergeSymbol + 1; j != i; ++j) + mergeSymbolLexem.append(j->lex.constData() + j->from + 1, j->len - 2); // append j->unquotedLexem() + mergeSymbolLexem.append('"'); + mergeSymbol->len = mergeSymbol->lex.length(); + mergeSymbol->from = 0; + i = symbols.erase(mergeSymbol + 1, i); + } + if (i == symbols.end()) + break; + } + } +} + void Preprocessor::preprocess(const QByteArray &filename, Symbols &preprocessed) { currentFilenames.push(filename); @@ -1020,7 +1058,8 @@ void Preprocessor::preprocess(const QByteArray &filename, Symbols &preprocessed) if (!file.open(QFile::ReadOnly)) continue; - QByteArray input = file.readAll(); + QByteArray input = readOrMapFile(&file); + file.close(); if (input.isEmpty()) continue; @@ -1153,9 +1192,10 @@ void Preprocessor::preprocess(const QByteArray &filename, Symbols &preprocessed) currentFilenames.pop(); } -Symbols Preprocessor::preprocessed(const QByteArray &filename, QIODevice *file) +Symbols Preprocessor::preprocessed(const QByteArray &filename, QFile *file) { - QByteArray input = file->readAll(); + QByteArray input = readOrMapFile(file); + if (input.isEmpty()) return symbols; @@ -1176,6 +1216,7 @@ Symbols Preprocessor::preprocessed(const QByteArray &filename, QIODevice *file) // phase 3: preprocess conditions and substitute macros Symbols result; preprocess(filename, result); + mergeStringLiterals(&result); #if 0 for (int j = 0; j < result.size(); ++j) diff --git a/src/tools/moc/preprocessor.h b/src/tools/moc/preprocessor.h index fc86781be8..77f3a30ac0 100644 --- a/src/tools/moc/preprocessor.h +++ b/src/tools/moc/preprocessor.h @@ -57,7 +57,7 @@ typedef SubArray MacroName; #endif typedef QHash<MacroName, Macro> Macros; -class QIODevice; +class QFile; class Preprocessor : public Parser { @@ -67,7 +67,7 @@ public: QList<QByteArray> frameworks; QSet<QByteArray> preprocessedIncludes; Macros macros; - Symbols preprocessed(const QByteArray &filename, QIODevice *device); + Symbols preprocessed(const QByteArray &filename, QFile *device); void parseDefineArguments(Macro *m); |