1*276da39aSCy Schubert //- Copyright (c) 2010 James Grenning and Contributed to Unity Project 2*276da39aSCy Schubert /* ========================================== 3*276da39aSCy Schubert Unity Project - A Test Framework for C 4*276da39aSCy Schubert Copyright (c) 2007 Mike Karlesky, Mark VanderVoord, Greg Williams 5*276da39aSCy Schubert [Released under MIT License. Please refer to license.txt for details] 6*276da39aSCy Schubert ========================================== */ 7*276da39aSCy Schubert 8*276da39aSCy Schubert #include <string.h> 9*276da39aSCy Schubert #include <stdio.h> 10*276da39aSCy Schubert #include "unity_fixture.h" 11*276da39aSCy Schubert #include "unity_internals.h" 12*276da39aSCy Schubert 13*276da39aSCy Schubert UNITY_FIXTURE_T UnityFixture; 14*276da39aSCy Schubert 15*276da39aSCy Schubert //If you decide to use the function pointer approach. 16*276da39aSCy Schubert int (*outputChar)(int) = putchar; 17*276da39aSCy Schubert 18*276da39aSCy Schubert int verbose = 0; 19*276da39aSCy Schubert 20*276da39aSCy Schubert void setUp(void); 21*276da39aSCy Schubert void tearDown(void); 22*276da39aSCy Schubert void setUp(void) { /*does nothing*/ } 23*276da39aSCy Schubert void tearDown(void) { /*does nothing*/ } 24*276da39aSCy Schubert 25*276da39aSCy Schubert static void announceTestRun(unsigned int runNumber) 26*276da39aSCy Schubert { 27*276da39aSCy Schubert UnityPrint("Unity test run "); 28*276da39aSCy Schubert UnityPrintNumber(runNumber+1); 29*276da39aSCy Schubert UnityPrint(" of "); 30*276da39aSCy Schubert UnityPrintNumber(UnityFixture.RepeatCount); 31*276da39aSCy Schubert UNITY_OUTPUT_CHAR('\n'); 32*276da39aSCy Schubert } 33*276da39aSCy Schubert 34*276da39aSCy Schubert int UnityMain(int argc, const char* argv[], void (*runAllTests)(void)) 35*276da39aSCy Schubert { 36*276da39aSCy Schubert int result = UnityGetCommandLineOptions(argc, argv); 37*276da39aSCy Schubert unsigned int r; 38*276da39aSCy Schubert if (result != 0) 39*276da39aSCy Schubert return result; 40*276da39aSCy Schubert 41*276da39aSCy Schubert for (r = 0; r < UnityFixture.RepeatCount; r++) 42*276da39aSCy Schubert { 43*276da39aSCy Schubert UnityBegin(argv[0]); 44*276da39aSCy Schubert announceTestRun(r); 45*276da39aSCy Schubert runAllTests(); 46*276da39aSCy Schubert UNITY_OUTPUT_CHAR('\n'); 47*276da39aSCy Schubert UnityEnd(); 48*276da39aSCy Schubert } 49*276da39aSCy Schubert 50*276da39aSCy Schubert return UnityFailureCount(); 51*276da39aSCy Schubert } 52*276da39aSCy Schubert 53*276da39aSCy Schubert static int selected(const char * filter, const char * name) 54*276da39aSCy Schubert { 55*276da39aSCy Schubert if (filter == 0) 56*276da39aSCy Schubert return 1; 57*276da39aSCy Schubert return strstr(name, filter) ? 1 : 0; 58*276da39aSCy Schubert } 59*276da39aSCy Schubert 60*276da39aSCy Schubert static int testSelected(const char* test) 61*276da39aSCy Schubert { 62*276da39aSCy Schubert return selected(UnityFixture.NameFilter, test); 63*276da39aSCy Schubert } 64*276da39aSCy Schubert 65*276da39aSCy Schubert static int groupSelected(const char* group) 66*276da39aSCy Schubert { 67*276da39aSCy Schubert return selected(UnityFixture.GroupFilter, group); 68*276da39aSCy Schubert } 69*276da39aSCy Schubert 70*276da39aSCy Schubert static void runTestCase(void) 71*276da39aSCy Schubert { 72*276da39aSCy Schubert 73*276da39aSCy Schubert } 74*276da39aSCy Schubert 75*276da39aSCy Schubert void UnityTestRunner(unityfunction* setup, 76*276da39aSCy Schubert unityfunction* testBody, 77*276da39aSCy Schubert unityfunction* teardown, 78*276da39aSCy Schubert const char * printableName, 79*276da39aSCy Schubert const char * group, 80*276da39aSCy Schubert const char * name, 81*276da39aSCy Schubert const char * file, int line) 82*276da39aSCy Schubert { 83*276da39aSCy Schubert if (testSelected(name) && groupSelected(group)) 84*276da39aSCy Schubert { 85*276da39aSCy Schubert Unity.CurrentTestFailed = 0; 86*276da39aSCy Schubert Unity.TestFile = file; 87*276da39aSCy Schubert Unity.CurrentTestName = printableName; 88*276da39aSCy Schubert Unity.CurrentTestLineNumber = line; 89*276da39aSCy Schubert if (!UnityFixture.Verbose) 90*276da39aSCy Schubert UNITY_OUTPUT_CHAR('.'); 91*276da39aSCy Schubert else 92*276da39aSCy Schubert UnityPrint(printableName); 93*276da39aSCy Schubert 94*276da39aSCy Schubert Unity.NumberOfTests++; 95*276da39aSCy Schubert UnityMalloc_StartTest(); 96*276da39aSCy Schubert UnityPointer_Init(); 97*276da39aSCy Schubert 98*276da39aSCy Schubert runTestCase(); 99*276da39aSCy Schubert if (TEST_PROTECT()) 100*276da39aSCy Schubert { 101*276da39aSCy Schubert setup(); 102*276da39aSCy Schubert testBody(); 103*276da39aSCy Schubert } 104*276da39aSCy Schubert if (TEST_PROTECT()) 105*276da39aSCy Schubert { 106*276da39aSCy Schubert teardown(); 107*276da39aSCy Schubert } 108*276da39aSCy Schubert if (TEST_PROTECT()) 109*276da39aSCy Schubert { 110*276da39aSCy Schubert UnityPointer_UndoAllSets(); 111*276da39aSCy Schubert if (!Unity.CurrentTestFailed) 112*276da39aSCy Schubert UnityMalloc_EndTest(); 113*276da39aSCy Schubert } 114*276da39aSCy Schubert UnityConcludeFixtureTest(); 115*276da39aSCy Schubert } 116*276da39aSCy Schubert } 117*276da39aSCy Schubert 118*276da39aSCy Schubert void UnityIgnoreTest(const char * printableName) 119*276da39aSCy Schubert { 120*276da39aSCy Schubert Unity.NumberOfTests++; 121*276da39aSCy Schubert Unity.CurrentTestIgnored = 1; 122*276da39aSCy Schubert if (!UnityFixture.Verbose) 123*276da39aSCy Schubert UNITY_OUTPUT_CHAR('!'); 124*276da39aSCy Schubert else 125*276da39aSCy Schubert UnityPrint(printableName); 126*276da39aSCy Schubert UnityConcludeFixtureTest(); 127*276da39aSCy Schubert } 128*276da39aSCy Schubert 129*276da39aSCy Schubert 130*276da39aSCy Schubert //------------------------------------------------- 131*276da39aSCy Schubert //Malloc and free stuff 132*276da39aSCy Schubert // 133*276da39aSCy Schubert #define MALLOC_DONT_FAIL -1 134*276da39aSCy Schubert static int malloc_count; 135*276da39aSCy Schubert static int malloc_fail_countdown = MALLOC_DONT_FAIL; 136*276da39aSCy Schubert 137*276da39aSCy Schubert void UnityMalloc_StartTest(void) 138*276da39aSCy Schubert { 139*276da39aSCy Schubert malloc_count = 0; 140*276da39aSCy Schubert malloc_fail_countdown = MALLOC_DONT_FAIL; 141*276da39aSCy Schubert } 142*276da39aSCy Schubert 143*276da39aSCy Schubert void UnityMalloc_EndTest(void) 144*276da39aSCy Schubert { 145*276da39aSCy Schubert malloc_fail_countdown = MALLOC_DONT_FAIL; 146*276da39aSCy Schubert if (malloc_count != 0) 147*276da39aSCy Schubert { 148*276da39aSCy Schubert TEST_FAIL_MESSAGE("This test leaks!"); 149*276da39aSCy Schubert } 150*276da39aSCy Schubert } 151*276da39aSCy Schubert 152*276da39aSCy Schubert void UnityMalloc_MakeMallocFailAfterCount(int countdown) 153*276da39aSCy Schubert { 154*276da39aSCy Schubert malloc_fail_countdown = countdown; 155*276da39aSCy Schubert } 156*276da39aSCy Schubert 157*276da39aSCy Schubert #ifdef malloc 158*276da39aSCy Schubert #undef malloc 159*276da39aSCy Schubert #endif 160*276da39aSCy Schubert 161*276da39aSCy Schubert #ifdef free 162*276da39aSCy Schubert #undef free 163*276da39aSCy Schubert #endif 164*276da39aSCy Schubert 165*276da39aSCy Schubert #ifdef calloc 166*276da39aSCy Schubert #undef calloc 167*276da39aSCy Schubert #endif 168*276da39aSCy Schubert 169*276da39aSCy Schubert #ifdef realloc 170*276da39aSCy Schubert #undef realloc 171*276da39aSCy Schubert #endif 172*276da39aSCy Schubert 173*276da39aSCy Schubert #include <stdlib.h> 174*276da39aSCy Schubert #include <string.h> 175*276da39aSCy Schubert 176*276da39aSCy Schubert typedef struct GuardBytes 177*276da39aSCy Schubert { 178*276da39aSCy Schubert size_t size; 179*276da39aSCy Schubert char guard[sizeof(size_t)]; 180*276da39aSCy Schubert } Guard; 181*276da39aSCy Schubert 182*276da39aSCy Schubert 183*276da39aSCy Schubert static const char * end = "END"; 184*276da39aSCy Schubert 185*276da39aSCy Schubert void * unity_malloc(size_t size) 186*276da39aSCy Schubert { 187*276da39aSCy Schubert char* mem; 188*276da39aSCy Schubert Guard* guard; 189*276da39aSCy Schubert 190*276da39aSCy Schubert if (malloc_fail_countdown != MALLOC_DONT_FAIL) 191*276da39aSCy Schubert { 192*276da39aSCy Schubert if (malloc_fail_countdown == 0) 193*276da39aSCy Schubert return 0; 194*276da39aSCy Schubert malloc_fail_countdown--; 195*276da39aSCy Schubert } 196*276da39aSCy Schubert 197*276da39aSCy Schubert malloc_count++; 198*276da39aSCy Schubert 199*276da39aSCy Schubert guard = (Guard*)malloc(size + sizeof(Guard) + 4); 200*276da39aSCy Schubert guard->size = size; 201*276da39aSCy Schubert mem = (char*)&(guard[1]); 202*276da39aSCy Schubert memcpy(&mem[size], end, strlen(end) + 1); 203*276da39aSCy Schubert 204*276da39aSCy Schubert return (void*)mem; 205*276da39aSCy Schubert } 206*276da39aSCy Schubert 207*276da39aSCy Schubert static int isOverrun(void * mem) 208*276da39aSCy Schubert { 209*276da39aSCy Schubert Guard* guard = (Guard*)mem; 210*276da39aSCy Schubert char* memAsChar = (char*)mem; 211*276da39aSCy Schubert guard--; 212*276da39aSCy Schubert 213*276da39aSCy Schubert return strcmp(&memAsChar[guard->size], end) != 0; 214*276da39aSCy Schubert } 215*276da39aSCy Schubert 216*276da39aSCy Schubert static void release_memory(void * mem) 217*276da39aSCy Schubert { 218*276da39aSCy Schubert Guard* guard = (Guard*)mem; 219*276da39aSCy Schubert guard--; 220*276da39aSCy Schubert 221*276da39aSCy Schubert malloc_count--; 222*276da39aSCy Schubert free(guard); 223*276da39aSCy Schubert } 224*276da39aSCy Schubert 225*276da39aSCy Schubert void unity_free(void * mem) 226*276da39aSCy Schubert { 227*276da39aSCy Schubert int overrun = isOverrun(mem);//strcmp(&memAsChar[guard->size], end) != 0; 228*276da39aSCy Schubert release_memory(mem); 229*276da39aSCy Schubert if (overrun) 230*276da39aSCy Schubert { 231*276da39aSCy Schubert TEST_FAIL_MESSAGE("Buffer overrun detected during free()"); 232*276da39aSCy Schubert } 233*276da39aSCy Schubert } 234*276da39aSCy Schubert 235*276da39aSCy Schubert void* unity_calloc(size_t num, size_t size) 236*276da39aSCy Schubert { 237*276da39aSCy Schubert void* mem = unity_malloc(num * size); 238*276da39aSCy Schubert memset(mem, 0, num*size); 239*276da39aSCy Schubert return mem; 240*276da39aSCy Schubert } 241*276da39aSCy Schubert 242*276da39aSCy Schubert void* unity_realloc(void * oldMem, size_t size) 243*276da39aSCy Schubert { 244*276da39aSCy Schubert Guard* guard = (Guard*)oldMem; 245*276da39aSCy Schubert // char* memAsChar = (char*)oldMem; 246*276da39aSCy Schubert void* newMem; 247*276da39aSCy Schubert 248*276da39aSCy Schubert if (oldMem == 0) 249*276da39aSCy Schubert return unity_malloc(size); 250*276da39aSCy Schubert 251*276da39aSCy Schubert guard--; 252*276da39aSCy Schubert if (isOverrun(oldMem)) 253*276da39aSCy Schubert { 254*276da39aSCy Schubert release_memory(oldMem); 255*276da39aSCy Schubert TEST_FAIL_MESSAGE("Buffer overrun detected during realloc()"); 256*276da39aSCy Schubert } 257*276da39aSCy Schubert 258*276da39aSCy Schubert if (size == 0) 259*276da39aSCy Schubert { 260*276da39aSCy Schubert release_memory(oldMem); 261*276da39aSCy Schubert return 0; 262*276da39aSCy Schubert } 263*276da39aSCy Schubert 264*276da39aSCy Schubert if (guard->size >= size) 265*276da39aSCy Schubert return oldMem; 266*276da39aSCy Schubert 267*276da39aSCy Schubert newMem = unity_malloc(size); 268*276da39aSCy Schubert memcpy(newMem, oldMem, guard->size); 269*276da39aSCy Schubert unity_free(oldMem); 270*276da39aSCy Schubert return newMem; 271*276da39aSCy Schubert } 272*276da39aSCy Schubert 273*276da39aSCy Schubert 274*276da39aSCy Schubert //-------------------------------------------------------- 275*276da39aSCy Schubert //Automatic pointer restoration functions 276*276da39aSCy Schubert typedef struct _PointerPair 277*276da39aSCy Schubert { 278*276da39aSCy Schubert struct _PointerPair * next; 279*276da39aSCy Schubert void ** pointer; 280*276da39aSCy Schubert void * old_value; 281*276da39aSCy Schubert } PointerPair; 282*276da39aSCy Schubert 283*276da39aSCy Schubert enum {MAX_POINTERS=50}; 284*276da39aSCy Schubert static PointerPair pointer_store[MAX_POINTERS]; 285*276da39aSCy Schubert static int pointer_index = 0; 286*276da39aSCy Schubert 287*276da39aSCy Schubert void UnityPointer_Init(void) 288*276da39aSCy Schubert { 289*276da39aSCy Schubert pointer_index = 0; 290*276da39aSCy Schubert } 291*276da39aSCy Schubert 292*276da39aSCy Schubert void UnityPointer_Set(void ** pointer, void * newValue) 293*276da39aSCy Schubert { 294*276da39aSCy Schubert if (pointer_index >= MAX_POINTERS) 295*276da39aSCy Schubert TEST_FAIL_MESSAGE("Too many pointers set"); 296*276da39aSCy Schubert 297*276da39aSCy Schubert pointer_store[pointer_index].pointer = pointer; 298*276da39aSCy Schubert pointer_store[pointer_index].old_value = *pointer; 299*276da39aSCy Schubert *pointer = newValue; 300*276da39aSCy Schubert pointer_index++; 301*276da39aSCy Schubert } 302*276da39aSCy Schubert 303*276da39aSCy Schubert void UnityPointer_UndoAllSets(void) 304*276da39aSCy Schubert { 305*276da39aSCy Schubert while (pointer_index > 0) 306*276da39aSCy Schubert { 307*276da39aSCy Schubert pointer_index--; 308*276da39aSCy Schubert *(pointer_store[pointer_index].pointer) = 309*276da39aSCy Schubert pointer_store[pointer_index].old_value; 310*276da39aSCy Schubert 311*276da39aSCy Schubert } 312*276da39aSCy Schubert } 313*276da39aSCy Schubert 314*276da39aSCy Schubert int UnityFailureCount(void) 315*276da39aSCy Schubert { 316*276da39aSCy Schubert return Unity.TestFailures; 317*276da39aSCy Schubert } 318*276da39aSCy Schubert 319*276da39aSCy Schubert int UnityGetCommandLineOptions(int argc, const char* argv[]) 320*276da39aSCy Schubert { 321*276da39aSCy Schubert int i; 322*276da39aSCy Schubert UnityFixture.Verbose = 0; 323*276da39aSCy Schubert UnityFixture.GroupFilter = 0; 324*276da39aSCy Schubert UnityFixture.NameFilter = 0; 325*276da39aSCy Schubert UnityFixture.RepeatCount = 1; 326*276da39aSCy Schubert 327*276da39aSCy Schubert if (argc == 1) 328*276da39aSCy Schubert return 0; 329*276da39aSCy Schubert 330*276da39aSCy Schubert for (i = 1; i < argc; ) 331*276da39aSCy Schubert { 332*276da39aSCy Schubert if (strcmp(argv[i], "-v") == 0) 333*276da39aSCy Schubert { 334*276da39aSCy Schubert UnityFixture.Verbose = 1; 335*276da39aSCy Schubert i++; 336*276da39aSCy Schubert } 337*276da39aSCy Schubert else if (strcmp(argv[i], "-g") == 0) 338*276da39aSCy Schubert { 339*276da39aSCy Schubert i++; 340*276da39aSCy Schubert if (i >= argc) 341*276da39aSCy Schubert return 1; 342*276da39aSCy Schubert UnityFixture.GroupFilter = argv[i]; 343*276da39aSCy Schubert i++; 344*276da39aSCy Schubert } 345*276da39aSCy Schubert else if (strcmp(argv[i], "-n") == 0) 346*276da39aSCy Schubert { 347*276da39aSCy Schubert i++; 348*276da39aSCy Schubert if (i >= argc) 349*276da39aSCy Schubert return 1; 350*276da39aSCy Schubert UnityFixture.NameFilter = argv[i]; 351*276da39aSCy Schubert i++; 352*276da39aSCy Schubert } 353*276da39aSCy Schubert else if (strcmp(argv[i], "-r") == 0) 354*276da39aSCy Schubert { 355*276da39aSCy Schubert UnityFixture.RepeatCount = 2; 356*276da39aSCy Schubert i++; 357*276da39aSCy Schubert if (i < argc) 358*276da39aSCy Schubert { 359*276da39aSCy Schubert if (*(argv[i]) >= '0' && *(argv[i]) <= '9') 360*276da39aSCy Schubert { 361*276da39aSCy Schubert UnityFixture.RepeatCount = atoi(argv[i]); 362*276da39aSCy Schubert i++; 363*276da39aSCy Schubert } 364*276da39aSCy Schubert } 365*276da39aSCy Schubert } else { 366*276da39aSCy Schubert // ignore unknown parameter 367*276da39aSCy Schubert i++; 368*276da39aSCy Schubert } 369*276da39aSCy Schubert } 370*276da39aSCy Schubert return 0; 371*276da39aSCy Schubert } 372*276da39aSCy Schubert 373*276da39aSCy Schubert void UnityConcludeFixtureTest(void) 374*276da39aSCy Schubert { 375*276da39aSCy Schubert if (Unity.CurrentTestIgnored) 376*276da39aSCy Schubert { 377*276da39aSCy Schubert if (UnityFixture.Verbose) 378*276da39aSCy Schubert { 379*276da39aSCy Schubert UNITY_OUTPUT_CHAR('\n'); 380*276da39aSCy Schubert } 381*276da39aSCy Schubert Unity.TestIgnores++; 382*276da39aSCy Schubert } 383*276da39aSCy Schubert else if (!Unity.CurrentTestFailed) 384*276da39aSCy Schubert { 385*276da39aSCy Schubert if (UnityFixture.Verbose) 386*276da39aSCy Schubert { 387*276da39aSCy Schubert UnityPrint(" PASS"); 388*276da39aSCy Schubert UNITY_OUTPUT_CHAR('\n'); 389*276da39aSCy Schubert } 390*276da39aSCy Schubert } 391*276da39aSCy Schubert else if (Unity.CurrentTestFailed) 392*276da39aSCy Schubert { 393*276da39aSCy Schubert Unity.TestFailures++; 394*276da39aSCy Schubert } 395*276da39aSCy Schubert 396*276da39aSCy Schubert Unity.CurrentTestFailed = 0; 397*276da39aSCy Schubert Unity.CurrentTestIgnored = 0; 398*276da39aSCy Schubert } 399