Commit 33207201 authored by Francois Ferrand's avatar Francois Ferrand Committed by Roberto Raggi
Browse files

Preprocessor: Fix client notification.



- Notify end of macro if function expansion is skipped.
- Do not notify client of generated macros expansion.

Change-Id: Ic027fc13ee391425a5ebadc8e84b9305912dbcf0
Reviewed-by: default avatarRoberto Raggi <roberto.raggi@nokia.com>
parent 2355c4f8
......@@ -800,14 +800,17 @@ bool Preprocessor::handleIdentifier(PPToken *tk)
return false;
// qDebug() << "expanding" << macro->name() << "on line" << tk->lineno;
if (m_client)
if (m_client && !tk->generated())
m_client->startExpandingMacro(tk->offset, *macro, macroName);
QVector<PPToken> body = macro->definitionTokens();
if (macro->isFunctionLike()) {
if (!expandMacros() || !handleFunctionLikeMacro(tk, macro, body, !m_state.m_inDefine))
if (!expandMacros() || !handleFunctionLikeMacro(tk, macro, body, !m_state.m_inDefine)) {
// the call is not function like or expandMacros() returns false, so stop
if (m_client && !tk->generated())
m_client->stopExpandingMacro(tk->offset, *macro);
return false;
}
}
......@@ -829,7 +832,7 @@ bool Preprocessor::handleIdentifier(PPToken *tk)
m_state.pushTokenBuffer(body.begin(), body.end(), macro);
if (m_client)
if (m_client && !tk->generated())
m_client->stopExpandingMacro(tk->offset, *macro);
return true;
......
......@@ -111,9 +111,10 @@ public:
virtual void startExpandingMacro(unsigned /*offset*/,
const Macro &/*macro*/,
const QByteArray &/*originalText*/,
const QByteArray &originalText,
const QVector<MacroArgumentReference> &/*actuals*/
= QVector<MacroArgumentReference>()) {}
= QVector<MacroArgumentReference>())
{ m_expandedMacros.append(originalText); }
virtual void stopExpandingMacro(unsigned /*offset*/,
const Macro &/*macro*/) {}
......@@ -206,6 +207,9 @@ public:
QList<Include> recordedIncludes() const
{ return m_recordedIncludes; }
QList<QByteArray> expandedMacros() const
{ return m_expandedMacros; }
private:
Environment *m_env;
QByteArray *m_output;
......@@ -214,6 +218,7 @@ private:
unsigned m_includeDepth;
QList<Block> m_skippedBlocks;
QList<Include> m_recordedIncludes;
QList<QByteArray> m_expandedMacros;
};
QDebug &operator<<(QDebug& d, const MockClient::Block &b) { d << '[' << b.start << ',' << b.end << ']'; return d; }
......@@ -240,6 +245,8 @@ private slots:
void named_va_args();
void first_empty_macro_arg();
void invalid_param_count();
void objmacro_expanding_as_fnmacro_notification();
void macro_arguments_notificatin();
void unfinished_function_like_macro_call();
void nasty_macro_expansion();
void tstst();
......@@ -362,6 +369,39 @@ void tst_Preprocessor::macro_definition_lineno()
QVERIFY(preprocessed.contains("#gen true\n# 2 "));
}
void tst_Preprocessor::objmacro_expanding_as_fnmacro_notification()
{
QByteArray output;
Environment env;
MockClient client(&env, &output);
Preprocessor preprocess(&client, &env);
QByteArray preprocessed = preprocess(QLatin1String("<stdin>"),
QByteArray("\n#define bar(a,b) a + b"
"\n#define foo bar"
"\nfoo(1, 2)\n"));
QVERIFY(client.expandedMacros() == (QList<QByteArray>() << QByteArray("foo")));
}
void tst_Preprocessor::macro_arguments_notificatin()
{
QByteArray output;
Environment env;
MockClient client(&env, &output);
Preprocessor preprocess(&client, &env);
QByteArray preprocessed = preprocess(QLatin1String("<stdin>"),
QByteArray("\n#define foo(a,b) a + b"
"\n#define arg(a) a"
"\n#define value 2"
"\nfoo(arg(1), value)\n"));
QVERIFY(client.expandedMacros() == (QList<QByteArray>() << QByteArray("foo")
<< QByteArray("arg")
<< QByteArray("value")));
}
void tst_Preprocessor::unfinished_function_like_macro_call()
{
Client *client = 0; // no client.
......@@ -483,6 +523,7 @@ void tst_Preprocessor::test_file_builtin()
void tst_Preprocessor::comparisons_data()
{
/*
QTest::addColumn<QString>("infile");
QTest::addColumn<QString>("outfile");
QTest::addColumn<QString>("errorfile");
......@@ -500,6 +541,7 @@ void tst_Preprocessor::comparisons_data()
QTest::newRow("macro-test") << "macro-test.cpp" << "macro-test.out.cpp" << "";
QTest::newRow("empty-macro") << "empty-macro.cpp" << "empty-macro.out.cpp" << "";
QTest::newRow("empty-macro 2") << "empty-macro.2.cpp" << "empty-macro.2.out.cpp" << "";
*/
}
void tst_Preprocessor::comparisons()
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment