gst_plugin_add_dependency hash collision using more than 5 environment variables
The hashing function left-shifts 5 bits per environment variable.
In Fluendo, we have noticed that when using more than 5 environment variable, collisions may happen, probably because unsigned int is only 32 bits.
For example the following code, does not trigger plugin re-scanning when setting LIBVA_DRIVER_NAME=iHD
.
const gchar *envvars[] = {
"LIBVA_DRIVER_NAME",
"LIBVA_DRIVER_PATH",
"VDPAU_DRIVER_PATH",
"VDPAU_DRIVER",
"DISPLAY",
"XDG_SESSION_TYPE",
"WAYLAND_DISPLAY",
"FLUVADEC_HW_BACKEND",
NULL
};
gst_plugin_add_dependency (
plugin, env, NULL, NULL, GST_PLUGIN_DEPENDENCY_FLAG_NONE);
This happens because hashes are the same whether setting or not LIBVA_DRIVER_NAME
environment variable.
Example of operations performed without setting LIBVA_DRIVER_NAME
:
guint sum = 0;
// LIBVA_DRIVER_NAME (unset)
sum = sum << 5;
// LIBVA_DRIVER_PATH (unset)
sum = sum << 5;
// VDPAU_DRIVER_PATH (unset)
sum = sum << 5;
// VDPAU_DRIVER (unset)
sum = sum << 5;
// DISPLAY=:0
sum = sum << 5;
sum += 5861871;
// XDG_SESSION_TYPE=wayland
sum = sum << 5;
sum += -1222592203;
// WAYLAND_DISPLAY=wayland-0
sum = sum << 5;
sum += 36954226;
// FLUVADEC_HW_BACKEND (unset)
sum = sum << 5;
// Result
// sum: -2108136896
Example of operations performed setting LIBVA_DRIVER_NAME
:
guint sum = 0;
// LIBVA_DRIVER_NAME=iHD
sum = sum << 5;
sum += 193493786; // hash calculated with g_str_hash, same in all cases
// LIBVA_DRIVER_PATH (unset)
sum = sum << 5;
// VDPAU_DRIVER_PATH (unset)
sum = sum << 5;
// VDPAU_DRIVER (unset)
sum = sum << 5;
// DISPLAY=:0
sum = sum << 5;
sum += 5861871;
// XDG_SESSION_TYPE=wayland
sum = sum << 5;
sum += -1222592203;
// WAYLAND_DISPLAY=wayland-0
sum = sum << 5;
sum += 36954226;
// FLUVADEC_HW_BACKEND (unset)
sum = sum << 5;
// Result:
// sum: -2108136896
As we can see, in both cases, hash is the same. This is a bug.
Workaround: Call gst_plugin_add_dependency each time per environment variable.