set_string_option_direct(
    char_u	*name,
    int		opt_idx,
    char_u	*val,
    int		opt_flags,	// OPT_FREE, OPT_LOCAL and/or OPT_GLOBAL
    int		set_sid UNUSED)
{
    char_u	*s;
    char_u	**varp;
    int		both = (opt_flags & (OPT_LOCAL | OPT_GLOBAL)) == 0;
    int		idx = opt_idx;

    if (idx == -1)		// use name
    {
	idx = findoption(name);
	if (idx < 0)	// not found (should not happen)
	{
	    semsg(_(e_intern2), "set_string_option_direct()");
	    siemsg(_("For option %s"), name);
	    return;
	}
    }

    if (is_hidden_option(idx))		// can't set hidden option
	return;

    s = vim_strsave(val);
    if (s != NULL)
    {
	varp = (char_u **)get_option_varp_scope(idx,
					       both ? OPT_LOCAL : opt_flags);
	if ((opt_flags & OPT_FREE) && (get_option_flags(idx) & P_ALLOCED))
	    free_string_option(*varp);
	*varp = s;

	// For buffer/window local option may also set the global value.
	if (both)
	    set_string_option_global(idx, varp);

	set_option_flag(idx, P_ALLOCED);

	// When setting both values of a global option with a local value,
	// make the local value empty, so that the global value is used.
	if (is_global_local_option(idx) && both)
	{
	    free_string_option(*varp);
	    *varp = empty_option;
	}
# ifdef FEAT_EVAL
	if (set_sid != SID_NONE)
	{
	    sctx_T script_ctx;

	    if (set_sid == 0)
		script_ctx = current_sctx;
	    else
	    {
		script_ctx.sc_sid = set_sid;
		script_ctx.sc_seq = 0;
		script_ctx.sc_lnum = 0;
		script_ctx.sc_version = 1;
	    }
	    set_option_sctx_idx(idx, opt_flags, script_ctx);
	}
# endif
    }
}
set_string_option_direct(
    char_u	*name,
    int		opt_idx,
    char_u	*val,
    int		opt_flags,	 
    int		set_sid UNUSED)
{
    char_u	*s;
    char_u	**varp;
    int		both = (opt_flags & (OPT_LOCAL | OPT_GLOBAL)) == 0;
    int		idx = opt_idx;

    if (idx == -1)		 
    {
	idx = findoption(name);
	if (idx < 0)	 
	{
	    semsg(_(e_intern2), "set_string_option_direct()");
	    siemsg(_("For option %s"), name);
	    return;
	}
    }

    if (is_hidden_option(idx))		 
	return;

    s = vim_strsave(val);
    if (s != NULL)
    {
	varp = (char_u **)get_option_varp_scope(idx,
					       both ? OPT_LOCAL : opt_flags);
	if ((opt_flags & OPT_FREE) && (get_option_flags(idx) & P_ALLOCED))
	    free_string_option(*varp);
	*varp = s;

	 
	if (both)
	    set_string_option_global(idx, varp);

	set_option_flag(idx, P_ALLOCED);

	 
	 
	if (is_global_local_option(idx) && both)
	{
	    free_string_option(*varp);
	    *varp = empty_option;
	}
# ifdef FEAT_EVAL
	if (set_sid != SID_NONE)
	{
	    sctx_T script_ctx;

	    if (set_sid == 0)
		script_ctx = current_sctx;
	    else
	    {
		script_ctx.sc_sid = set_sid;
		script_ctx.sc_seq = 0;
		script_ctx.sc_lnum = 0;
		script_ctx.sc_version = 1;
	    }
	    set_option_sctx_idx(idx, opt_flags, script_ctx);
	}
# endif
    }
}