ThrowTheSwitch / Ceedling

Ruby-based unit testing and build system for C projects

Home Page:http://throwtheswitch.org

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

different test results when running gcov

lafonso-gnrc opened this issue · comments

Hello,

I am currently using snapshot, ceedling-0.32.0-164e950.

I've encountered a possible issue. The situation showed up when testing a function that was missing a return statement. example:

uint32_t get_register(uint32_t id)
{
  uint32_t return_vale = 0;

  return_value = gpio_ports[id]->DIR;


}

void test_register()
{
  uint32_t result = 0;
  GPIOA->DIR = 1;

  result = get_register(0);

  TEST_ASSERT_EQUAL_UINT32(1, 1);
}

Keep in mind the function did more than this, the register access was an inline function and I didn't try it with this specific example.
The registers are process memory.

The ceedling test:all passed - the return values were always what was expected.
gcov ran fine, creates report but the command line reports failures, basically it returns the input parameter "id"

I just find it weird that the behaviour is different.
I've realized gcov doesn't take the same compilation flags - I think I fixed that now, but regardless it seems weird to me

Hi. This makes sense, actually. To operate, gcov injects a lot of additional code into your project, allowing it to keep track of your paths through the codebase. This is called "instrumenting" your code for measurement. This instrumentation is part of the executable, and therefore effects what's in memory.

When you're dealing with uninitialized memory (for example, not actually filling out a return value), then there's no guarantee as to WHAT is in that memory. Sometimes it might work, sometimes it won't... depending on what else has run before it. Right now you're seeing a gcov vs non-gcov behavior... but this bug is even more annoying than that! You might even be able to change the outcome by making changes to tests that run BEFORE this test is called. It all depends on what's happening on the stack and other memory.

A good way to avoid these kinds of issues in the future is to tell gcc that a missing return value is an error. Unfortunately, you can't necessarily pick and choose which warnings get bumped to errors... but adding -Werror will make all your warnings into errors, and then you can control which warnings you care about.

hello,

Thank you, that makes sense! I am faintly aware that the outcome is undefined.

We did just add warning into errors and been trying to tidy up our configuration for our needs.
For this specific issue we have selectively turned on some -Werror. We might end up turning them all on. But this is what we got In case someone stumbles over this

:flags:
  :release:
    :compile:
      :*:
        - -Wall
        - -Werror=return-type
  :test:
    :compile:
      :*:
        - -Wall
        - -Werror=return-type
  :gcov:
      :compile:  
        :*:
          - -Wall
          - -Werror=return-type

So overall, there is no issue with ceedling related to this.