diff --git a/options/m_config.c b/options/m_config.c index 318ced3d34..52a9b2f6d8 100644 --- a/options/m_config.c +++ b/options/m_config.c @@ -1538,7 +1538,7 @@ static void find_opt(struct m_config_shadow *shadow, struct m_config_data *data, } } -void m_config_cache_write_opt(struct m_config_cache *cache, void *ptr) +bool m_config_cache_write_opt(struct m_config_cache *cache, void *ptr) { struct config_cache *in = cache->internal; struct m_config_shadow *shadow = in->shadow; @@ -1559,17 +1559,22 @@ void m_config_cache_write_opt(struct m_config_cache *cache, void *ptr) struct m_group_data *gsrc = m_config_gdata(in->src, group_idx); assert(gdst && gsrc); - m_option_copy(opt, gsrc->udata + opt->offset, ptr); + bool changed = !m_option_equal(opt, gsrc->udata + opt->offset, ptr); + if (changed) { + m_option_copy(opt, gsrc->udata + opt->offset, ptr); - gsrc->ts = atomic_fetch_add(&shadow->ts, 1) + 1; + gsrc->ts = atomic_fetch_add(&shadow->ts, 1) + 1; - for (int n = 0; n < shadow->num_listeners; n++) { - struct config_cache *listener = shadow->listeners[n]; - if (listener->wakeup_cb && m_config_gdata(listener->data, group_idx)) - listener->wakeup_cb(listener->wakeup_cb_ctx); + for (int n = 0; n < shadow->num_listeners; n++) { + struct config_cache *listener = shadow->listeners[n]; + if (listener->wakeup_cb && m_config_gdata(listener->data, group_idx)) + listener->wakeup_cb(listener->wakeup_cb_ctx); + } } pthread_mutex_unlock(&shadow->lock); + + return changed; } void m_config_notify_change_co(struct m_config *config, diff --git a/options/m_config.h b/options/m_config.h index 357dca5d4d..f62bc9670f 100644 --- a/options/m_config.h +++ b/options/m_config.h @@ -340,7 +340,8 @@ bool m_config_cache_get_next_changed(struct m_config_cache *cache, void **out_pt // call. // ptr: points to any field in cache->opts that is managed by an option. If // this is not the case, the function crashes for your own good. -void m_config_cache_write_opt(struct m_config_cache *cache, void *ptr); +// returns: if true, this was an update; if false, shadow had same value +bool m_config_cache_write_opt(struct m_config_cache *cache, void *ptr); // Like m_config_cache_alloc(), but return the struct (m_config_cache->opts) // directly, with no way to update the config. Basically this returns a copy