ISR(TIMER0_OVF_vect)
{
unsigned long m = timer0_millis;
:
timer0_millis = m;
timer0_overflow_count++;
// New code
TIMER_OVF_Callback();
}
TIMER0_OVF_Callback would be initialized to point to a null function, and would have an API to set it to an arbitrary user function (just like attachInterrupt().)
It's actually a pretty bad idea. The was ISRs work on AVR, having any function call in your ISR causes a rather large number of additional expensive instructions to be added to save and restore context that is defined by the C ABI as "callee changeable."