protected static function fill_preferences_cache() {
        if (self::$preferencescache !== null) {
            return;
        }

        // Array of user preferences and expected types/values.
        // Every preference that can be updated directly by user should be added here.
        $preferences = array();
        $preferences['auth_forcepasswordchange'] = array('type' => PARAM_INT, 'null' => NULL_NOT_ALLOWED, 'choices' => array(0, 1),
            'permissioncallback' => function($user, $preferencename) {
                global $USER;
                $systemcontext = context_system::instance();
                return ($USER->id != $user->id && (has_capability('moodle/user:update', $systemcontext) ||
                        ($user->timecreated > time() - 10 && has_capability('moodle/user:create', $systemcontext))));
            });
        $preferences['usemodchooser'] = array('type' => PARAM_INT, 'null' => NULL_NOT_ALLOWED, 'default' => 1,
            'choices' => array(0, 1));
        $preferences['forum_markasreadonnotification'] = array('type' => PARAM_INT, 'null' => NULL_NOT_ALLOWED, 'default' => 1,
            'choices' => array(0, 1));
        $preferences['htmleditor'] = array('type' => PARAM_NOTAGS, 'null' => NULL_ALLOWED,
            'cleancallback' => function($value, $preferencename) {
                if (empty($value) || !array_key_exists($value, core_component::get_plugin_list('editor'))) {
                    return null;
                }
                return $value;
            });
        $preferences['badgeprivacysetting'] = array('type' => PARAM_INT, 'null' => NULL_NOT_ALLOWED, 'default' => 1,
            'choices' => array(0, 1), 'permissioncallback' => function($user, $preferencename) {
                global $CFG, $USER;
                return !empty($CFG->enablebadges) && $user->id == $USER->id;
            });
        $preferences['blogpagesize'] = array('type' => PARAM_INT, 'null' => NULL_NOT_ALLOWED, 'default' => 10,
            'permissioncallback' => function($user, $preferencename) {
                global $USER;
                return $USER->id == $user->id && has_capability('moodle/blog:view', context_system::instance());
            });

        // Core components that may want to define their preferences.
        // List of core components implementing callback is hardcoded here for performance reasons.
        // TODO MDL-58184 cache list of core components implementing a function.
        $corecomponents = ['core_message', 'core_calendar'];
        foreach ($corecomponents as $component) {
            if (($pluginpreferences = component_callback($component, 'user_preferences')) && is_array($pluginpreferences)) {
                $preferences += $pluginpreferences;
            }
        }

        // Plugins that may define their preferences.
        if ($pluginsfunction = get_plugins_with_function('user_preferences')) {
            foreach ($pluginsfunction as $plugintype => $plugins) {
                foreach ($plugins as $function) {
                    if (($pluginpreferences = call_user_func($function)) && is_array($pluginpreferences)) {
                        $preferences += $pluginpreferences;
                    }
                }
            }
        }

        self::$preferencescache = $preferences;
    }