tests/auto/selftests/tst_selftests.cpp
changeset 25 e24348a560a6
parent 23 89e065397ea6
child 30 5dc02b23752f
equal deleted inserted replaced
23:89e065397ea6 25:e24348a560a6
   115 static QList<QByteArray> splitLines(QByteArray ba)
   115 static QList<QByteArray> splitLines(QByteArray ba)
   116 {
   116 {
   117     ba.replace('\r', "");
   117     ba.replace('\r', "");
   118     QList<QByteArray> out = ba.split('\n');
   118     QList<QByteArray> out = ba.split('\n');
   119 
   119 
   120     // Replace any ` file="..."' in XML with a generic location.
   120     // Replace any ` file="..."' or ` line="..."'  in XML with a generic location.
   121     static const char marker[] = " file=\"";
   121     static const char *markers[][2] = {
       
   122         { " file=\"", " file=\"__FILE__\"" },
       
   123         { " line=\"", " line=\"__LINE__\"" }
       
   124     };
       
   125     static const int markerCount = sizeof markers / sizeof markers[0];
       
   126 
   122     for (int i = 0; i < out.size(); ++i) {
   127     for (int i = 0; i < out.size(); ++i) {
   123         QByteArray& line = out[i];
   128         QByteArray& line = out[i];
   124         int index = line.indexOf(marker);
   129         for (int j = 0; j < markerCount; ++j) {
   125         if (index == -1) {
   130             int index = line.indexOf(markers[j][0]);
   126             continue;
   131             if (index == -1) {
   127         }
   132                 continue;
   128         int end = line.indexOf('"', index + sizeof(marker));
   133             }
   129         if (end == -1) {
   134             int end = line.indexOf('"', index + strlen(markers[j][0]));
   130             continue;
   135             if (end == -1) {
   131         }
   136                 continue;
   132         line.replace(index, end-index, " file=\"__FILE__\"");
   137             }
       
   138             line.replace(index, end-index + 1, markers[j][1]);
       
   139         }
   133     }
   140     }
   134 
   141 
   135     return out;
   142     return out;
   136 }
   143 }
   137 
   144 
   394             continue;
   401             continue;
   395         if (line.endsWith(" : failure location"))
   402         if (line.endsWith(" : failure location"))
   396             continue;
   403             continue;
   397 
   404 
   398         const QString output(QString::fromLatin1(line));
   405         const QString output(QString::fromLatin1(line));
   399         const QString expected(QString::fromLatin1(exp.at(i)).replace("<INSERT_QT_VERSION_HERE>", QT_VERSION_STR));
   406         const QString expected(QString::fromLatin1(exp.at(i)).replace("@INSERT_QT_VERSION_HERE@", QT_VERSION_STR));
   400 
   407 
   401         if (line.contains("ASSERT") && output != expected) {
   408         if (line.contains("ASSERT") && output != expected) {
   402             QEXPECT_FAIL("assert",          "QTestLib prints out the absolute path.", Continue);
   409             QEXPECT_FAIL("assert",          "QTestLib prints out the absolute path.", Continue);
   403             QEXPECT_FAIL("assert xml",      "QTestLib prints out the absolute path.", Continue);
   410             QEXPECT_FAIL("assert xml",      "QTestLib prints out the absolute path.", Continue);
   404             QEXPECT_FAIL("assert xml flush","QTestLib prints out the absolute path.", Continue);
   411             QEXPECT_FAIL("assert xml flush","QTestLib prints out the absolute path.", Continue);
   419             else {
   426             else {
   420                 /*
   427                 /*
   421                    Are we expecting this line to be a benchmark result?
   428                    Are we expecting this line to be a benchmark result?
   422                    If so, don't do a literal comparison, since results have some natural variance.
   429                    If so, don't do a literal comparison, since results have some natural variance.
   423                 */
   430                 */
   424                 if (benchmark) {
   431                 if (benchmark || line.startsWith("<BenchmarkResult")) {
   425                     QString error;
   432                     QString error;
   426 
   433 
   427                     BenchmarkResult actualResult = BenchmarkResult::parse(output, &error);
   434                     BenchmarkResult actualResult = BenchmarkResult::parse(output, &error);
   428                     QVERIFY2(error.isEmpty(), qPrintable(QString("Actual line didn't parse as benchmark result: %1\nLine: %2").arg(error).arg(output)));
   435                     QVERIFY2(error.isEmpty(), qPrintable(QString("Actual line didn't parse as benchmark result: %1\nLine: %2").arg(error).arg(output)));
   429 
   436 
   449     QFETCH(QStringList, arguments);
   456     QFETCH(QStringList, arguments);
   450 
   457 
   451     doRunSubTest(subdir, logger, arguments);
   458     doRunSubTest(subdir, logger, arguments);
   452 }
   459 }
   453 
   460 
       
   461 // attribute must contain ="
       
   462 QString extractXmlAttribute(const QString &line, const char *attribute)
       
   463 {
       
   464     int index = line.indexOf(attribute);
       
   465     if (index == -1)
       
   466         return QString();
       
   467     int end = line.indexOf('"', index + strlen(attribute));
       
   468     if (end == -1)
       
   469         return QString();
       
   470 
       
   471     QString result = line.mid(index + strlen(attribute), end - index - strlen(attribute));
       
   472     if (result.isEmpty())
       
   473         return ""; // ensure empty but not null
       
   474     return result;
       
   475 }
       
   476 
   454 /* Parse line into the BenchmarkResult it represents. */
   477 /* Parse line into the BenchmarkResult it represents. */
   455 BenchmarkResult BenchmarkResult::parse(QString const& line, QString* error)
   478 BenchmarkResult BenchmarkResult::parse(QString const& line, QString* error)
   456 {
   479 {
   457     if (error) *error = QString();
   480     if (error) *error = QString();
   458     BenchmarkResult out;
   481     BenchmarkResult out;
   461 
   484 
   462     if (remaining.isEmpty()) {
   485     if (remaining.isEmpty()) {
   463         if (error) *error = "Line is empty";
   486         if (error) *error = "Line is empty";
   464         return out;
   487         return out;
   465     }
   488     }
       
   489 
       
   490     if (line.startsWith("<BenchmarkResult ")) {
       
   491         // XML result
       
   492         // format:
       
   493         //   <BenchmarkResult metric="$unit" tag="$tag" value="$total" iterations="$iterations" />
       
   494         if (!line.endsWith("/>")) {
       
   495             if (error) *error = "unterminated XML";
       
   496             return out;
       
   497         }
       
   498 
       
   499         QString unit = extractXmlAttribute(line, " metric=\"");
       
   500         QString sTotal = extractXmlAttribute(line, " value=\"");
       
   501         QString sIterations = extractXmlAttribute(line, " iterations=\"");
       
   502         if (unit.isNull() || sTotal.isNull() || sIterations.isNull()) {
       
   503             if (error) *error = "XML snippet did not contain all required values";
       
   504             return out;
       
   505         }
       
   506 
       
   507         bool ok;
       
   508 #if QT_VERSION >= 0x040700
       
   509         // Qt 4.7 uses floating point
       
   510         double total = sTotal.toDouble(&ok);
       
   511         if (!ok) {
       
   512             if (error) *error = sTotal + " is not a valid number";
       
   513             return out;
       
   514         }
       
   515         double iterations = sIterations.toDouble(&ok);
       
   516         if (!ok) {
       
   517             if (error) *error = sIterations + " is not a valid number";
       
   518             return out;
       
   519         }
       
   520 #else
       
   521         qlonglong total = sTotal.toLongLong(&ok);
       
   522         if (!ok) {
       
   523             if (error) *error = sTotal + " is not a valid integer";
       
   524             return out;
       
   525         }
       
   526         qlonglong iterations = sIterations.toLongLong(&ok);
       
   527         if (!ok) {
       
   528             if (error) *error = sIterations + " is not a valid integer";
       
   529             return out;
       
   530         }
       
   531 #endif
       
   532 
       
   533         out.unit = unit;
       
   534         out.total = total;
       
   535         out.iterations = iterations;
       
   536         return out;
       
   537     }
       
   538     // Text result
   466 
   539 
   467     /* This code avoids using a QRegExp because QRegExp might be broken. */
   540     /* This code avoids using a QRegExp because QRegExp might be broken. */
   468 
   541 
   469     /* Sample format: 4,000 msec per iteration (total: 4000, iterations: 1) */
   542     /* Sample format: 4,000 msec per iteration (total: 4000, iterations: 1) */
   470 
   543