Another, not uncommon solution would be to use a function-like macro right away, e.g.
#define MY_FUNC_DEFAULTS() myFunc(10, 15, true)
This looks also fairly clean, retains the function syntax etc. Note that the macro expansion does not end with a semicolon so that it can (and must) be provided at the call site in the natural fashion: if(cond) MY_FUNC_DEFAULTS(); else g();
works as expected.
Because you originally asked about C++: I find some of the OCD types here a bit annoying. All preprocessor solutions provided in the answers here work equally well in both languages. Nonetheless, the preprocessor is text replacement and as such inherently unsafe. Therefore, C++ provides means to avoid using it. In this case one could provide default arguments in the function declaration:
void myFunc(uint8_t temp = 10, uint32_t value = 15, bool valid = true);
This essentially overloads the function: It defines a set of four distinct functions that take 3, 2, 1 or 0 arguments, respectively. All of the calls
myFunc();
myFunc(1);
myFunc(1,2);
myFunc(1,2,false);
are now possible.
Such declarations could be present in different translation units with different default values. The default values are defined at the caller side and are not part of the function signature. (Whether that would be recommended is debatable though.)