CppUTest is a C /C++ based unit xUnit test framework for unit testing and for test-driving your code.

CppUTest

Where to find more information

Getting test reports on the console

You may need to tailor the file src/Platforms/mbed/UtestPlatform.cpp to your needs. In particular, if you want console output, you might want to look at the function PlatformSpecificPutchar().

Quick introduction (some code!)

To write your first test, all you need is a new cpp file with a TEST_GROUP and a TEST, like:

#include "CppUTest/TestHarness.h"

TEST_GROUP(FirstTestGroup)
{
};

TEST(FirstTestGroup, FirstTest)
{
   FAIL("Fail me!");
}

This test will fail.

You can add new tests to the test group by just writing more tests in the file, like this:

TEST(FirstTestGroup, SecondTest)
{
   STRCMP_EQUAL("hello", "world");
   LONGS_EQUAL(1, 2);
   CHECK(false);
}

You do need to trigger the tests from somewhere in your program. It could look something like:

#include "CppUTest/TestRegistry.h"
#include "CppUTest/CommandLineTestRunner.h"

int main(int ac, char** av)
{
    ....
    unsigned failureCount = 0;
    {
        ConsoleTestOutput output;
        CommandLineTestRunner runner(ac, av, &output, TestRegistry::getCurrentRegistry());
        failureCount = runner.runAllTestsMain();
    }

    if (failureCount == 0) {
        console.printf("PASSED\r\n");
    }
    ...
}

For more information, We’d recommend to read the manual or, even better, check some existing tests such as SimpleStringTest or (a bit more complicated) MemoryLeakDetectorTest or the mocking tests or just check out the Cheat Sheet.

Committer:
Rohit Grover
Date:
Thu Jun 19 08:24:31 2014 +0100
Revision:
2:82161d9e7b36
Parent:
1:4769360130ed
uncomment the code in CommandLineTestRunner::RunAllTests() having to do with MemoryLeakWarningPlugin

Bas Vodde, from the CppUTest development team has suggested an alternate way to run tests.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
Rohit Grover 1:4769360130ed 1 /*
Rohit Grover 1:4769360130ed 2 * Copyright (c) 2007, Michael Feathers, James Grenning and Bas Vodde
Rohit Grover 1:4769360130ed 3 * All rights reserved.
Rohit Grover 1:4769360130ed 4 *
Rohit Grover 1:4769360130ed 5 * Redistribution and use in source and binary forms, with or without
Rohit Grover 1:4769360130ed 6 * modification, are permitted provided that the following conditions are met:
Rohit Grover 1:4769360130ed 7 * * Redistributions of source code must retain the above copyright
Rohit Grover 1:4769360130ed 8 * notice, this list of conditions and the following disclaimer.
Rohit Grover 1:4769360130ed 9 * * Redistributions in binary form must reproduce the above copyright
Rohit Grover 1:4769360130ed 10 * notice, this list of conditions and the following disclaimer in the
Rohit Grover 1:4769360130ed 11 * documentation and/or other materials provided with the distribution.
Rohit Grover 1:4769360130ed 12 * * Neither the name of the <organization> nor the
Rohit Grover 1:4769360130ed 13 * names of its contributors may be used to endorse or promote products
Rohit Grover 1:4769360130ed 14 * derived from this software without specific prior written permission.
Rohit Grover 1:4769360130ed 15 *
Rohit Grover 1:4769360130ed 16 * THIS SOFTWARE IS PROVIDED BY THE EARLIER MENTIONED AUTHORS ``AS IS'' AND ANY
Rohit Grover 1:4769360130ed 17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
Rohit Grover 1:4769360130ed 18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
Rohit Grover 1:4769360130ed 19 * DISCLAIMED. IN NO EVENT SHALL <copyright holder> BE LIABLE FOR ANY
Rohit Grover 1:4769360130ed 20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
Rohit Grover 1:4769360130ed 21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
Rohit Grover 1:4769360130ed 22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
Rohit Grover 1:4769360130ed 23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
Rohit Grover 1:4769360130ed 24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
Rohit Grover 1:4769360130ed 25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
Rohit Grover 1:4769360130ed 26 */
Rohit Grover 1:4769360130ed 27
Rohit Grover 1:4769360130ed 28 #include "CppUTest/TestHarness.h"
Rohit Grover 1:4769360130ed 29 #include "CppUTest/CommandLineTestRunner.h"
Rohit Grover 1:4769360130ed 30 #include "CppUTest/TestOutput.h"
Rohit Grover 1:4769360130ed 31 #include "CppUTest/JUnitTestOutput.h"
Rohit Grover 1:4769360130ed 32 #include "CppUTest/TestRegistry.h"
Rohit Grover 1:4769360130ed 33
Rohit Grover 1:4769360130ed 34 CommandLineTestRunner::CommandLineTestRunner(int ac, const char** av, TestOutput* output, TestRegistry* registry) :
Rohit Grover 1:4769360130ed 35 output_(output), jUnitOutput_(NULL), arguments_(NULL), registry_(registry)
Rohit Grover 1:4769360130ed 36 {
Rohit Grover 1:4769360130ed 37 arguments_ = new CommandLineArguments(ac, av);
Rohit Grover 1:4769360130ed 38 }
Rohit Grover 1:4769360130ed 39
Rohit Grover 1:4769360130ed 40 CommandLineTestRunner::~CommandLineTestRunner()
Rohit Grover 1:4769360130ed 41 {
Rohit Grover 1:4769360130ed 42 delete arguments_;
Rohit Grover 1:4769360130ed 43 delete jUnitOutput_;
Rohit Grover 1:4769360130ed 44 }
Rohit Grover 1:4769360130ed 45
Rohit Grover 1:4769360130ed 46 int CommandLineTestRunner::RunAllTests(int ac, char** av)
Rohit Grover 1:4769360130ed 47 {
Rohit Grover 1:4769360130ed 48 return RunAllTests(ac, const_cast<const char**> (av));
Rohit Grover 1:4769360130ed 49 }
Rohit Grover 1:4769360130ed 50
Rohit Grover 1:4769360130ed 51 int CommandLineTestRunner::RunAllTests(int ac, const char** av)
Rohit Grover 1:4769360130ed 52 {
Rohit Grover 1:4769360130ed 53 int result = 0;
Rohit Grover 1:4769360130ed 54 ConsoleTestOutput output;
Rohit Grover 1:4769360130ed 55
Rohit Grover 2:82161d9e7b36 56 MemoryLeakWarningPlugin memLeakWarn(DEF_PLUGIN_MEM_LEAK);
Rohit Grover 2:82161d9e7b36 57 memLeakWarn.destroyGlobalDetectorAndTurnOffMemoryLeakDetectionInDestructor(true);
Rohit Grover 2:82161d9e7b36 58 TestRegistry::getCurrentRegistry()->installPlugin(&memLeakWarn);
Rohit Grover 1:4769360130ed 59
Rohit Grover 1:4769360130ed 60 {
Rohit Grover 1:4769360130ed 61 CommandLineTestRunner runner(ac, av, &output, TestRegistry::getCurrentRegistry());
Rohit Grover 1:4769360130ed 62 result = runner.runAllTestsMain();
Rohit Grover 1:4769360130ed 63 }
Rohit Grover 1:4769360130ed 64
Rohit Grover 2:82161d9e7b36 65 if (result == 0) {
Rohit Grover 2:82161d9e7b36 66 output << memLeakWarn.FinalReport(0);
Rohit Grover 2:82161d9e7b36 67 }
Rohit Grover 2:82161d9e7b36 68 TestRegistry::getCurrentRegistry()->removePluginByName(DEF_PLUGIN_MEM_LEAK);
Rohit Grover 1:4769360130ed 69 return result;
Rohit Grover 1:4769360130ed 70 }
Rohit Grover 1:4769360130ed 71
Rohit Grover 1:4769360130ed 72 int CommandLineTestRunner::runAllTestsMain()
Rohit Grover 1:4769360130ed 73 {
Rohit Grover 1:4769360130ed 74 int testResult = 0;
Rohit Grover 1:4769360130ed 75
Rohit Grover 1:4769360130ed 76 SetPointerPlugin pPlugin(DEF_PLUGIN_SET_POINTER);
Rohit Grover 1:4769360130ed 77 registry_->installPlugin(&pPlugin);
Rohit Grover 1:4769360130ed 78
Rohit Grover 1:4769360130ed 79 if (parseArguments(registry_->getFirstPlugin()))
Rohit Grover 1:4769360130ed 80 testResult = runAllTests();
Rohit Grover 1:4769360130ed 81
Rohit Grover 1:4769360130ed 82 registry_->removePluginByName(DEF_PLUGIN_SET_POINTER);
Rohit Grover 1:4769360130ed 83 return testResult;
Rohit Grover 1:4769360130ed 84 }
Rohit Grover 1:4769360130ed 85
Rohit Grover 1:4769360130ed 86 void CommandLineTestRunner::initializeTestRun()
Rohit Grover 1:4769360130ed 87 {
Rohit Grover 1:4769360130ed 88 registry_->groupFilter(arguments_->getGroupFilter());
Rohit Grover 1:4769360130ed 89 registry_->nameFilter(arguments_->getNameFilter());
Rohit Grover 1:4769360130ed 90 if (arguments_->isVerbose()) output_->verbose();
Rohit Grover 1:4769360130ed 91 if (arguments_->runTestsInSeperateProcess()) registry_->setRunTestsInSeperateProcess();
Rohit Grover 1:4769360130ed 92 }
Rohit Grover 1:4769360130ed 93
Rohit Grover 1:4769360130ed 94 int CommandLineTestRunner::runAllTests()
Rohit Grover 1:4769360130ed 95 {
Rohit Grover 1:4769360130ed 96 initializeTestRun();
Rohit Grover 1:4769360130ed 97 int loopCount = 0;
Rohit Grover 1:4769360130ed 98 int failureCount = 0;
Rohit Grover 1:4769360130ed 99 int repeat_ = arguments_->getRepeatCount();
Rohit Grover 1:4769360130ed 100
Rohit Grover 1:4769360130ed 101 while (loopCount++ < repeat_) {
Rohit Grover 1:4769360130ed 102 output_->printTestRun(loopCount, repeat_);
Rohit Grover 1:4769360130ed 103 TestResult tr(*output_);
Rohit Grover 1:4769360130ed 104 registry_->runAllTests(tr);
Rohit Grover 1:4769360130ed 105 failureCount += tr.getFailureCount();
Rohit Grover 1:4769360130ed 106 }
Rohit Grover 1:4769360130ed 107
Rohit Grover 1:4769360130ed 108 return failureCount;
Rohit Grover 1:4769360130ed 109 }
Rohit Grover 1:4769360130ed 110
Rohit Grover 1:4769360130ed 111 bool CommandLineTestRunner::parseArguments(TestPlugin* plugin)
Rohit Grover 1:4769360130ed 112 {
Rohit Grover 1:4769360130ed 113 if (arguments_->parse(plugin)) {
Rohit Grover 1:4769360130ed 114 if (arguments_->isJUnitOutput()) {
Rohit Grover 1:4769360130ed 115 output_ = jUnitOutput_ = new JUnitTestOutput;
Rohit Grover 1:4769360130ed 116 if (jUnitOutput_ != NULL) {
Rohit Grover 1:4769360130ed 117 jUnitOutput_->setPackageName(arguments_->getPackageName());
Rohit Grover 1:4769360130ed 118 }
Rohit Grover 1:4769360130ed 119 }
Rohit Grover 1:4769360130ed 120 return true;
Rohit Grover 1:4769360130ed 121 }
Rohit Grover 1:4769360130ed 122 else {
Rohit Grover 1:4769360130ed 123 output_->print(arguments_->usage());
Rohit Grover 1:4769360130ed 124 return false;
Rohit Grover 1:4769360130ed 125 }
Rohit Grover 1:4769360130ed 126 }
Rohit Grover 1:4769360130ed 127
Rohit Grover 1:4769360130ed 128 bool CommandLineTestRunner::isVerbose()
Rohit Grover 1:4769360130ed 129 {
Rohit Grover 1:4769360130ed 130 return arguments_->isVerbose();
Rohit Grover 1:4769360130ed 131 }
Rohit Grover 1:4769360130ed 132
Rohit Grover 1:4769360130ed 133 int CommandLineTestRunner::getRepeatCount()
Rohit Grover 1:4769360130ed 134 {
Rohit Grover 1:4769360130ed 135 return arguments_->getRepeatCount();
Rohit Grover 1:4769360130ed 136 }
Rohit Grover 1:4769360130ed 137
Rohit Grover 1:4769360130ed 138 TestFilter CommandLineTestRunner::getGroupFilter()
Rohit Grover 1:4769360130ed 139 {
Rohit Grover 1:4769360130ed 140 return arguments_->getGroupFilter();
Rohit Grover 1:4769360130ed 141 }
Rohit Grover 1:4769360130ed 142
Rohit Grover 1:4769360130ed 143 TestFilter CommandLineTestRunner::getNameFilter()
Rohit Grover 1:4769360130ed 144 {
Rohit Grover 1:4769360130ed 145 return arguments_->getNameFilter();
Rohit Grover 1:4769360130ed 146 }