/* vi:set ts=8 sts=4 sw=4 noet:
 *
 * VIM - Vi IMproved	by Bram Moolenaar
 *
 * Do ":help uganda"  in Vim to read copying and usage conditions.
 * Do ":help credits" in Vim to see a list of people who contributed.
 * See README.txt for an overview of the Vim source code.
 */

/*
 * ex_eval.c: functions for Ex command line for the +eval feature.
 */

#include "vim.h"

#if defined(FEAT_EVAL) || defined(PROTO)

static int	throw_exception(void *, except_type_T, char_u *);
static char_u	*get_end_emsg(struct condstack *cstack);

/*
 * Exception handling terms:
 *
 *	:try		":try" command		\
 *	    ...		try block		|
 *	:catch RE	":catch" command	|
 *	    ...		catch clause		|- try conditional
 *	:finally	":finally" command	|
 *	    ...		finally clause		|
 *	:endtry		":endtry" command	/
 *
 * The try conditional may have any number of catch clauses and at most one
 * finally clause.  A ":throw" command can be inside the try block, a catch
 * clause, the finally clause, or in a function called or script sourced from
 * there or even outside the try conditional.  Try conditionals may be nested.
 */

/*
 * Configuration whether an exception is thrown on error or interrupt.  When
 * the preprocessor macros below evaluate to FALSE, an error (did_emsg) or
 * interrupt (got_int) under an active try conditional terminates the script
 * after the non-active finally clauses of all active try conditionals have been
 * executed.  Otherwise, errors and/or interrupts are converted into catchable
 * exceptions (did_throw additionally set), which terminate the script only if
 * not caught.  For user exceptions, only did_throw is set.  (Note: got_int can
 * be set asynchronously afterwards by a SIGINT, so did_throw && got_int is not
 * a reliant test that the exception currently being thrown is an interrupt
 * exception.  Similarly, did_emsg can be set afterwards on an error in an
 * (unskipped) conditional command inside an inactive conditional, so did_throw
 * && did_emsg is not a reliant test that the exception currently being thrown
 * is an error exception.)  -  The macros can be defined as expressions checking
 * for a variable that is allowed to be changed during execution of a script.
 */
#if 0
/* Expressions used for testing during the development phase. */
# define THROW_ON_ERROR		(!eval_to_number("$VIMNOERRTHROW"))
# define THROW_ON_INTERRUPT	(!eval_to_number("$VIMNOINTTHROW"))
# define THROW_TEST
#else
/* Values used for the Vim release. */
# define THROW_ON_ERROR		TRUE
# define THROW_ON_ERROR_TRUE
# define THROW_ON_INTERRUPT	TRUE
# define THROW_ON_INTERRUPT_TRUE
#endif

/*
 * When several errors appear in a row, setting "force_abort" is delayed until
 * the failing command returned.  "cause_abort" is set to TRUE meanwhile, in
 * order to indicate that situation.  This is useful when "force_abort" was set
 * during execution of a function call from an expression: the aborting of the
 * expression evaluation is done without producing any error messages, but all
 * error messages on parsing errors during the expression evaluation are given
 * (even if a try conditional is active).
 */
static int cause_abort = FALSE;

/*
 * Return TRUE when immediately aborting on error, or when an interrupt
 * occurred or an exception was thrown but not caught.  Use for ":{range}call"
 * to check whether an aborted function that does not handle a range itself
 * should be called again for the next line in the range.  Also used for
 * cancelling expression evaluation after a function call caused an immediate
 * abort.  Note that the first emsg() call temporarily resets "force_abort"
 * until the throw point for error messages has been reached.  That is, during
 * cancellation of an expression evaluation after an aborting function call or
 * due to a parsing error, aborting() always returns the same value.
 */
    int
aborting(void)
{
    return (did_emsg && force_abort) || got_int || did_throw;
}

/*
 * The value of "force_abort" is temporarily reset by the first emsg() call
 * during an expression evaluation, and "cause_abort" is used instead.  It might
 * be necessary to restore "force_abort" even before the throw point for the
 * error message has been reached.  update_force_abort() should be called then.
 */
    void
update_force_abort(void)
{
    if (cause_abort)
	force_abort = TRUE;
}

/*
 * Return TRUE if a command with a subcommand resulting in "retcode" should
 * abort the script processing.  Can be used to suppress an autocommand after
 * execution of a failing subcommand as long as the error message has not been
 * displayed and actually caused the abortion.
 */
    int
should_abort(int retcode)
{
    return ((retcode == FAIL && trylevel != 0 && !emsg_silent) || aborting());
}

/*
 * Return TRUE if a function with the "abort" flag should not be considered
 * ended on an error.  This means that parsing commands is continued in order
 * to find finally clauses to be executed, and that some errors in skipped
 * commands are still reported.
 */
    int
aborted_in_try(void)
{
    /* This function is only called after an error.  In this case, "force_abort"
     * determines whether searching for finally clauses is necessary. */
    return force_abort;
}

/*
 * cause_errthrow(): Cause a throw of an error exception if appropriate.
 * Return TRUE if the error message should not be displayed by emsg().
 * Sets "ignore", if the emsg() call should be ignored completely.
 *
 * When several messages appear in the same command, the first is usually the
 * most specific one and used as the exception value.  The "severe" flag can be
 * set to TRUE, if a later but severer message should be used instead.
 */
    int
cause_errthrow(
    char_u	*mesg,
    int		severe,
    int		*ignore)
{
    struct msglist *elem;
    struct msglist **plist;

    /*
     * Do nothing when displaying the interrupt message or reporting an
     * uncaught exception (which has already been discarded then) at the top
     * level.  Also when no exception can be thrown.  The message will be
     * displayed by emsg().
     */
    if (suppress_errthrow)
	return FALSE;

    /*
     * If emsg() has not been called previously, temporarily reset
     * "force_abort" until the throw point for error messages has been
     * reached.  This ensures that aborting() returns the same value for all
     * errors that appear in the same command.  This means particularly that
     * for parsing errors during expression evaluation emsg() will be called
     * multiply, even when the expression is evaluated from a finally clause
     * that was activated due to an aborting error, interrupt, or exception.
     */
    if (!did_emsg)
    {
	cause_abort = force_abort;
	force_abort = FALSE;
    }

    /*
     * If no try conditional is active and no exception is being thrown and
     * there has not been an error in a try conditional or a throw so far, do
     * nothing (for compatibility of non-EH scripts).  The message will then
     * be displayed by emsg().  When ":silent!" was used and we are not
     * currently throwing an exception, do nothing.  The message text will
     * then be stored to v:errmsg by emsg() without displaying it.
     */
    if (((trylevel == 0 && !cause_abort) || emsg_silent) && !did_throw)
	return FALSE;

    /*
     * Ignore an interrupt message when inside a try conditional or when an
     * exception is being thrown or when an error in a try conditional or
     * throw has been detected previously.  This is important in order that an
     * interrupt exception is catchable by the innermost try conditional and
     * not replaced by an interrupt message error exception.
     */
    if (mesg == (char_u *)_(e_interr))
    {
	*ignore = TRUE;
	return TRUE;
    }

    /*
     * Ensure that all commands in nested function calls and sourced files
     * are aborted immediately.
     */
    cause_abort = TRUE;

    /*
     * When an exception is being thrown, some commands (like conditionals) are
     * not skipped.  Errors in those commands may affect what of the subsequent
     * commands are regarded part of catch and finally clauses.  Catching the
     * exception would then cause execution of commands not intended by the
     * user, who wouldn't even get aware of the problem.  Therefor, discard the
     * exception currently being thrown to prevent it from being caught.  Just
     * execute finally clauses and terminate.
     */
    if (did_throw)
    {
	/* When discarding an interrupt exception, reset got_int to prevent the
	 * same interrupt being converted to an exception again and discarding
	 * the error exception we are about to throw here. */
	if (current_exception->type == ET_INTERRUPT)
	    got_int = FALSE;
	discard_current_exception();
    }

#ifdef THROW_TEST
    if (!THROW_ON_ERROR)
    {
	/*
	 * Print error message immediately without searching for a matching
	 * catch clause; just finally clauses are executed before the script
	 * is terminated.
	 */
	return FALSE;
    }
    else
#endif
    {
	/*
	 * Prepare the throw of an error exception, so that everything will
	 * be aborted (except for executing finally clauses), until the error
	 * exception is caught; if still uncaught at the top level, the error
	 * message will be displayed and the script processing terminated
	 * then.  -  This function has no access to the conditional stack.
	 * Thus, the actual throw is made after the failing command has
	 * returned.  -  Throw only the first of several errors in a row, except
	 * a severe error is following.
	 */
	if (msg_list != NULL)
	{
	    plist = msg_list;
	    while (*plist != NULL)
		plist = &(*plist)->next;

	    elem = (struct msglist *)alloc((unsigned)sizeof(struct msglist));
	    if (elem == NULL)
	    {
		suppress_errthrow = TRUE;
		EMSG(_(e_outofmem));
	    }
	    else
	    {
		elem->msg = vim_strsave(mesg);
		if (elem->msg == NULL)
		{
		    vim_free(elem);
		    suppress_errthrow = TRUE;
		    EMSG(_(e_outofmem));
		}
		else
		{
		    elem->next = NULL;
		    elem->throw_msg = NULL;
		    *plist = elem;
		    if (plist == msg_list || severe)
		    {
			char_u	    *tmsg;

			/* Skip the extra "Vim " prefix for message "E458". */
			tmsg = elem->msg;
			if (STRNCMP(tmsg, "Vim E", 5) == 0
				&& VIM_ISDIGIT(tmsg[5])
				&& VIM_ISDIGIT(tmsg[6])
				&& VIM_ISDIGIT(tmsg[7])
				&& tmsg[8] == ':'
				&& tmsg[9] == ' ')
			    (*msg_list)->throw_msg = &tmsg[4];
			else
			    (*msg_list)->throw_msg = tmsg;
		    }
		}
	    }
	}
	return TRUE;
    }
}

/*
 * Free a "msg_list" and the messages it contains.
 */
    static void
free_msglist(struct msglist *l)
{
    struct msglist  *messages, *next;

    messages = l;
    while (messages != NULL)
    {
	next = messages->next;
	vim_free(messages->msg);
	vim_free(messages);
	messages = next;
    }
}

/*
 * Free global "*msg_list" and the messages it contains, then set "*msg_list"
 * to NULL.
 */
    void
free_global_msglist(void)
{
    free_msglist(*msg_list);
    *msg_list = NULL;
}

/*
 * Throw the message specified in the call to cause_errthrow() above as an
 * error exception.  If cstack is NULL, postpone the throw until do_cmdline()
 * has returned (see do_one_cmd()).
 */
    void
do_errthrow(struct condstack *cstack, char_u *cmdname)
{
    /*
     * Ensure that all commands in nested function calls and sourced files
     * are aborted immediately.
     */
    if (cause_abort)
    {
	cause_abort = FALSE;
	force_abort = TRUE;
    }

    /* If no exception is to be thrown or the conversion should be done after
     * returning to a previous invocation of do_one_cmd(), do nothing. */
    if (msg_list == NULL || *msg_list == NULL)
	return;

    if (throw_exception(*msg_list, ET_ERROR, cmdname) == FAIL)
	free_msglist(*msg_list);
    else
    {
	if (cstack != NULL)
	    do_throw(cstack);
	else
	    need_rethrow = TRUE;
    }
    *msg_list = NULL;
}

/*
 * do_intthrow(): Replace the current exception by an interrupt or interrupt
 * exception if appropriate.  Return TRUE if the current exception is discarded,
 * FALSE otherwise.
 */
    int
do_intthrow(struct condstack *cstack)
{
    /*
     * If no interrupt occurred or no try conditional is active and no exception
     * is being thrown, do nothing (for compatibility of non-EH scripts).
     */
    if (!got_int || (trylevel == 0 && !did_throw))
	return FALSE;

#ifdef THROW_TEST	/* avoid warning for condition always true */
    if (!THROW_ON_INTERRUPT)
    {
	/*
	 * The interrupt aborts everything except for executing finally clauses.
	 * Discard any user or error or interrupt exception currently being
	 * thrown.
	 */
	if (did_throw)
	    discard_current_exception();
    }
    else
#endif
    {
	/*
	 * Throw an interrupt exception, so that everything will be aborted
	 * (except for executing finally clauses), until the interrupt exception
	 * is caught; if still uncaught at the top level, the script processing
	 * will be terminated then.  -  If an interrupt exception is already
	 * being thrown, do nothing.
	 *
	 */
	if (did_throw)
	{
	    if (current_exception->type == ET_INTERRUPT)
		return FALSE;

	    /* An interrupt exception replaces any user or error exception. */
	    discard_current_exception();
	}
	if (throw_exception("Vim:Interrupt", ET_INTERRUPT, NULL) != FAIL)
	    do_throw(cstack);
    }

    return TRUE;
}

/*
 * Get an exception message that is to be stored in current_exception->value.
 */
    char_u *
get_exception_string(
    void	*value,
    except_type_T type,
    char_u	*cmdname,
    int		*should_free)
{
    char_u	*ret, *mesg;
    int		cmdlen;
    char_u	*p, *val;

    if (type == ET_ERROR)
    {
	*should_free = TRUE;
	mesg = ((struct msglist *)value)->throw_msg;
	if (cmdname != NULL && *cmdname != NUL)
	{
	    cmdlen = (int)STRLEN(cmdname);
	    ret = vim_strnsave((char_u *)"Vim(",
					   4 + cmdlen + 2 + (int)STRLEN(mesg));
	    if (ret == NULL)
		return ret;
	    STRCPY(&ret[4], cmdname);
	    STRCPY(&ret[4 + cmdlen], "):");
	    val = ret + 4 + cmdlen + 2;
	}
	else
	{
	    ret = vim_strnsave((char_u *)"Vim:", 4 + (int)STRLEN(mesg));
	    if (ret == NULL)
		return ret;
	    val = ret + 4;
	}

	/* msg_add_fname may have been used to prefix the message with a file
	 * name in quotes.  In the exception value, put the file name in
	 * parentheses and move it to the end. */
	for (p = mesg; ; p++)
	{
	    if (*p == NUL
		    || (*p == 'E'
			&& VIM_ISDIGIT(p[1])
			&& (p[2] == ':'
			    || (VIM_ISDIGIT(p[2])
				&& (p[3] == ':'
				    || (VIM_ISDIGIT(p[3])
					&& p[4] == ':'))))))
	    {
		if (*p == NUL || p == mesg)
		    STRCAT(val, mesg);  /* 'E123' missing or at beginning */
		else
		{
		    /* '"filename" E123: message text' */
		    if (mesg[0] != '"' || p-2 < &mesg[1] ||
			    p[-2] != '"' || p[-1] != ' ')
			/* "E123:" is part of the file name. */
			continue;

		    STRCAT(val, p);
		    p[-2] = NUL;
		    sprintf((char *)(val + STRLEN(p)), " (%s)", &mesg[1]);
		    p[-2] = '"';
		}
		break;
	    }
	}
    }
    else
    {
	*should_free = FALSE;
	ret = (char_u *)value;
    }

    return ret;
}


/*
 * Throw a new exception.  Return FAIL when out of memory or it was tried to
 * throw an illegal user exception.  "value" is the exception string for a
 * user or interrupt exception, or points to a message list in case of an
 * error exception.
 */
    static int
throw_exception(void *value, except_type_T type, char_u *cmdname)
{
    except_T	*excp;
    int		should_free;

    /*
     * Disallow faking Interrupt or error exceptions as user exceptions.  They
     * would be treated differently from real interrupt or error exceptions
     * when no active try block is found, see do_cmdline().
     */
    if (type == ET_USER)
    {
	if (STRNCMP((char_u *)value, "Vim", 3) == 0
		&& (((char_u *)value)[3] == NUL || ((char_u *)value)[3] == ':'
		    || ((char_u *)value)[3] == '('))
	{
	    EMSG(_("E608: Cannot :throw exceptions with 'Vim' prefix"));
	    goto fail;
	}
    }

    excp = (except_T *)alloc((unsigned)sizeof(except_T));
    if (excp == NULL)
	goto nomem;

    if (type == ET_ERROR)
	/* Store the original message and prefix the exception value with
	 * "Vim:" or, if a command name is given, "Vim(cmdname):". */
	excp->messages = (struct msglist *)value;

    excp->value = get_exception_string(value, type, cmdname, &should_free);
    if (excp->value == NULL && should_free)
	goto nomem;

    excp->type = type;
    excp->throw_name = vim_strsave(sourcing_name == NULL
					      ? (char_u *)"" : sourcing_name);
    if (excp->throw_name == NULL)
    {
	if (should_free)
	    vim_free(excp->value);
	goto nomem;
    }
    excp->throw_lnum = sourcing_lnum;

    if (p_verbose >= 13 || debug_break_level > 0)
    {
	int	save_msg_silent = msg_silent;

	if (debug_break_level > 0)
	    msg_silent = FALSE;		/* display messages */
	else
	    verbose_enter();
	++no_wait_return;
	if (debug_break_level > 0 || *p_vfile == NUL)
	    msg_scroll = TRUE;	    /* always scroll up, don't overwrite */

	smsg((char_u *)_("Exception thrown: %s"), excp->value);
	msg_puts((char_u *)"\n");   /* don't overwrite this either */

	if (debug_break_level > 0 || *p_vfile == NUL)
	    cmdline_row = msg_row;
	--no_wait_return;
	if (debug_break_level > 0)
	    msg_silent = save_msg_silent;
	else
	    verbose_leave();
    }

    current_exception = excp;
    return OK;

nomem:
    vim_free(excp);
    suppress_errthrow = TRUE;
    EMSG(_(e_outofmem));
fail:
    current_exception = NULL;
    return FAIL;
}

/*
 * Discard an exception.  "was_finished" is set when the exception has been
 * caught and the catch clause has been ended normally.
 */
    static void
discard_exception(except_T *excp, int was_finished)
{
    char_u		*saved_IObuff;

    if (excp == NULL)
    {
	internal_error("discard_exception()");
	return;
    }

    if (p_verbose >= 13 || debug_break_level > 0)
    {
	int	save_msg_silent = msg_silent;

	saved_IObuff = vim_strsave(IObuff);
	if (debug_break_level > 0)
	    msg_silent = FALSE;		/* display messages */
	else
	    verbose_enter();
	++no_wait_return;
	if (debug_break_level > 0 || *p_vfile == NUL)
	    msg_scroll = TRUE;	    /* always scroll up, don't overwrite */
	smsg(was_finished
		    ? (char_u *)_("Exception finished: %s")
		    : (char_u *)_("Exception discarded: %s"),
		excp->value);
	msg_puts((char_u *)"\n");   /* don't overwrite this either */
	if (debug_break_level > 0 || *p_vfile == NUL)
	    cmdline_row = msg_row;
	--no_wait_return;
	if (debug_break_level > 0)
	    msg_silent = save_msg_silent;
	else
	    verbose_leave();
	STRCPY(IObuff, saved_IObuff);
	vim_free(saved_IObuff);
    }
    if (excp->type != ET_INTERRUPT)
	vim_free(excp->value);
    if (excp->type == ET_ERROR)
	free_msglist(excp->messages);
    vim_free(excp->throw_name);
    vim_free(excp);
}

/*
 * Discard the exception currently being thrown.
 */
    void
discard_current_exception(void)
{
    if (current_exception != NULL)
    {
	discard_exception(current_exception, FALSE);
	current_exception = NULL;
    }
    did_throw = FALSE;
    need_rethrow = FALSE;
}

/*
 * Put an exception on the caught stack.
 */
    static void
catch_exception(except_T *excp)
{
    excp->caught = caught_stack;
    caught_stack = excp;
    set_vim_var_string(VV_EXCEPTION, excp->value, -1);
    if (*excp->throw_name != NUL)
    {
	if (excp->throw_lnum != 0)
	    vim_snprintf((char *)IObuff, IOSIZE, _("%s, line %ld"),
				    excp->throw_name, (long)excp->throw_lnum);
	else
	    vim_snprintf((char *)IObuff, IOSIZE, "%s", excp->throw_name);
	set_vim_var_string(VV_THROWPOINT, IObuff, -1);
    }
    else
	/* throw_name not set on an exception from a command that was typed. */
	set_vim_var_string(VV_THROWPOINT, NULL, -1);

    if (p_verbose >= 13 || debug_break_level > 0)
    {
	int	save_msg_silent = msg_silent;

	if (debug_break_level > 0)
	    msg_silent = FALSE;		/* display messages */
	else
	    verbose_enter();
	++no_wait_return;
	if (debug_break_level > 0 || *p_vfile == NUL)
	    msg_scroll = TRUE;	    /* always scroll up, don't overwrite */

	smsg((char_u *)_("Exception caught: %s"), excp->value);
	msg_puts((char_u *)"\n");   /* don't overwrite this either */

	if (debug_break_level > 0 || *p_vfile == NUL)
	    cmdline_row = msg_row;
	--no_wait_return;
	if (debug_break_level > 0)
	    msg_silent = save_msg_silent;
	else
	    verbose_leave();
    }
}

/*
 * Remove an exception from the caught stack.
 */
    static void
finish_exception(except_T *excp)
{
    if (excp != caught_stack)
	internal_error("finish_exception()");
    caught_stack = caught_stack->caught;
    if (caught_stack != NULL)
    {
	set_vim_var_string(VV_EXCEPTION, caught_stack->value, -1);
	if (*caught_stack->throw_name != NUL)
	{
	    if (caught_stack->throw_lnum != 0)
		vim_snprintf((char *)IObuff, IOSIZE,
			_("%s, line %ld"), caught_stack->throw_name,
			(long)caught_stack->throw_lnum);
	    else
		vim_snprintf((char *)IObuff, IOSIZE, "%s",
						    caught_stack->throw_name);
	    set_vim_var_string(VV_THROWPOINT, IObuff, -1);
	}
	else
	    /* throw_name not set on an exception from a command that was
	     * typed. */
	    set_vim_var_string(VV_THROWPOINT, NULL, -1);
    }
    else
    {
	set_vim_var_string(VV_EXCEPTION, NULL, -1);
	set_vim_var_string(VV_THROWPOINT, NULL, -1);
    }

    /* Discard the exception, but use the finish message for 'verbose'. */
    discard_exception(excp, TRUE);
}

/*
 * Flags specifying the message displayed by report_pending.
 */
#define RP_MAKE		0
#define RP_RESUME	1
#define RP_DISCARD	2

/*
 * Report information about something pending in a finally clause if required by
 * the 'verbose' option or when debugging.  "action" tells whether something is
 * made pending or something pending is resumed or discarded.  "pending" tells
 * what is pending.  "value" specifies the return value for a pending ":return"
 * or the exception value for a pending exception.
 */
    static void
report_pending(int action, int pending, void *value)
{
    char_u	*mesg;
    char	*s;
    int		save_msg_silent;


    switch (action)
    {
	case RP_MAKE:
	    mesg = (char_u *)_("%s made pending");
	    break;
	case RP_RESUME:
	    mesg = (char_u *)_("%s resumed");
	    break;
	/* case RP_DISCARD: */
	default:
	    mesg = (char_u *)_("%s discarded");
	    break;
    }

    switch (pending)
    {
	case CSTP_NONE:
	    return;

	case CSTP_CONTINUE:
	    s = ":continue";
	    break;
	case CSTP_BREAK:
	    s = ":break";
	    break;
	case CSTP_FINISH:
	    s = ":finish";
	    break;
	case CSTP_RETURN:
	    /* ":return" command producing value, allocated */
	    s = (char *)get_return_cmd(value);
	    break;

	default:
	    if (pending & CSTP_THROW)
	    {
		vim_snprintf((char *)IObuff, IOSIZE,
						(char *)mesg, _("Exception"));
		mesg = vim_strnsave(IObuff, (int)STRLEN(IObuff) + 4);
		STRCAT(mesg, ": %s");
		s = (char *)((except_T *)value)->value;
	    }
	    else if ((pending & CSTP_ERROR) && (pending & CSTP_INTERRUPT))
		s = _("Error and interrupt");
	    else if (pending & CSTP_ERROR)
		s = _("Error");
	    else /* if (pending & CSTP_INTERRUPT) */
		s = _("Interrupt");
    }

    save_msg_silent = msg_silent;
    if (debug_break_level > 0)
	msg_silent = FALSE;	/* display messages */
    ++no_wait_return;
    msg_scroll = TRUE;		/* always scroll up, don't overwrite */
    smsg(mesg, (char_u *)s);
    msg_puts((char_u *)"\n");   /* don't overwrite this either */
    cmdline_row = msg_row;
    --no_wait_return;
    if (debug_break_level > 0)
	msg_silent = save_msg_silent;

    if (pending == CSTP_RETURN)
	vim_free(s);
    else if (pending & CSTP_THROW)
	vim_free(mesg);
}

/*
 * If something is made pending in a finally clause, report it if required by
 * the 'verbose' option or when debugging.
 */
    void
report_make_pending(int pending, void *value)
{
    if (p_verbose >= 14 || debug_break_level > 0)
    {
	if (debug_break_level <= 0)
	    verbose_enter();
	report_pending(RP_MAKE, pending, value);
	if (debug_break_level <= 0)
	    verbose_leave();
    }
}

/*
 * If something pending in a finally clause is resumed at the ":endtry", report
 * it if required by the 'verbose' option or when debugging.
 */
    void
report_resume_pending(int pending, void *value)
{
    if (p_verbose >= 14 || debug_break_level > 0)
    {
	if (debug_break_level <= 0)
	    verbose_enter();
	report_pending(RP_RESUME, pending, value);
	if (debug_break_level <= 0)
	    verbose_leave();
    }
}

/*
 * If something pending in a finally clause is discarded, report it if required
 * by the 'verbose' option or when debugging.
 */
    void
report_discard_pending(int pending, void *value)
{
    if (p_verbose >= 14 || debug_break_level > 0)
    {
	if (debug_break_level <= 0)
	    verbose_enter();
	report_pending(RP_DISCARD, pending, value);
	if (debug_break_level <= 0)
	    verbose_leave();
    }
}


/*
 * ":if".
 */
    void
ex_if(exarg_T *eap)
{
    int		error;
    int		skip;
    int		result;
    struct condstack	*cstack = eap->cstack;

    if (cstack->cs_idx == CSTACK_LEN - 1)
	eap->errmsg = (char_u *)N_("E579: :if nesting too deep");
    else
    {
	++cstack->cs_idx;
	cstack->cs_flags[cstack->cs_idx] = 0;

	/*
	 * Don't do something after an error, interrupt, or throw, or when there
	 * is a surrounding conditional and it was not active.
	 */
	skip = did_emsg || got_int || did_throw || (cstack->cs_idx > 0
		&& !(cstack->cs_flags[cstack->cs_idx - 1] & CSF_ACTIVE));

	result = eval_to_bool(eap->arg, &error, &eap->nextcmd, skip);

	if (!skip && !error)
	{
	    if (result)
		cstack->cs_flags[cstack->cs_idx] = CSF_ACTIVE | CSF_TRUE;
	}
	else
	    /* set TRUE, so this conditional will never get active */
	    cstack->cs_flags[cstack->cs_idx] = CSF_TRUE;
    }
}

/*
 * ":endif".
 */
    void
ex_endif(exarg_T *eap)
{
    did_endif = TRUE;
    if (eap->cstack->cs_idx < 0
	    || (eap->cstack->cs_flags[eap->cstack->cs_idx]
					   & (CSF_WHILE | CSF_FOR | CSF_TRY)))
	eap->errmsg = (char_u *)N_("E580: :endif without :if");
    else
    {
	/*
	 * When debugging or a breakpoint was encountered, display the debug
	 * prompt (if not already done).  This shows the user that an ":endif"
	 * is executed when the ":if" or a previous ":elseif" was not TRUE.
	 * Handle a ">quit" debug command as if an interrupt had occurred before
	 * the ":endif".  That is, throw an interrupt exception if appropriate.
	 * Doing this here prevents an exception for a parsing error being
	 * discarded by throwing the interrupt exception later on.
	 */
	if (!(eap->cstack->cs_flags[eap->cstack->cs_idx] & CSF_TRUE)
						    && dbg_check_skipped(eap))
	    (void)do_intthrow(eap->cstack);

	--eap->cstack->cs_idx;
    }
}

/*
 * ":else" and ":elseif".
 */
    void
ex_else(exarg_T *eap)
{
    int		error;
    int		skip;
    int		result;
    struct condstack	*cstack = eap->cstack;

    /*
     * Don't do something after an error, interrupt, or throw, or when there is
     * a surrounding conditional and it was not active.
     */
    skip = did_emsg || got_int || did_throw || (cstack->cs_idx > 0
	    && !(cstack->cs_flags[cstack->cs_idx - 1] & CSF_ACTIVE));

    if (cstack->cs_idx < 0
	    || (cstack->cs_flags[cstack->cs_idx]
					   & (CSF_WHILE | CSF_FOR | CSF_TRY)))
    {
	if (eap->cmdidx == CMD_else)
	{
	    eap->errmsg = (char_u *)N_("E581: :else without :if");
	    return;
	}
	eap->errmsg = (char_u *)N_("E582: :elseif without :if");
	skip = TRUE;
    }
    else if (cstack->cs_flags[cstack->cs_idx] & CSF_ELSE)
    {
	if (eap->cmdidx == CMD_else)
	{
	    eap->errmsg = (char_u *)N_("E583: multiple :else");
	    return;
	}
	eap->errmsg = (char_u *)N_("E584: :elseif after :else");
	skip = TRUE;
    }

    /* if skipping or the ":if" was TRUE, reset ACTIVE, otherwise set it */
    if (skip || cstack->cs_flags[cstack->cs_idx] & CSF_TRUE)
    {
	if (eap->errmsg == NULL)
	    cstack->cs_flags[cstack->cs_idx] = CSF_TRUE;
	skip = TRUE;	/* don't evaluate an ":elseif" */
    }
    else
	cstack->cs_flags[cstack->cs_idx] = CSF_ACTIVE;

    /*
     * When debugging or a breakpoint was encountered, display the debug prompt
     * (if not already done).  This shows the user that an ":else" or ":elseif"
     * is executed when the ":if" or previous ":elseif" was not TRUE.  Handle
     * a ">quit" debug command as if an interrupt had occurred before the
     * ":else" or ":elseif".  That is, set "skip" and throw an interrupt
     * exception if appropriate.  Doing this here prevents that an exception
     * for a parsing errors is discarded when throwing the interrupt exception
     * later on.
     */
    if (!skip && dbg_check_skipped(eap) && got_int)
    {
	(void)do_intthrow(cstack);
	skip = TRUE;
    }

    if (eap->cmdidx == CMD_elseif)
    {
	result = eval_to_bool(eap->arg, &error, &eap->nextcmd, skip);
	/* When throwing error exceptions, we want to throw always the first
	 * of several errors in a row.  This is what actually happens when
	 * a conditional error was detected above and there is another failure
	 * when parsing the expression.  Since the skip flag is set in this
	 * case, the parsing error will be ignored by emsg(). */

	if (!skip && !error)
	{
	    if (result)
		cstack->cs_flags[cstack->cs_idx] = CSF_ACTIVE | CSF_TRUE;
	    else
		cstack->cs_flags[cstack->cs_idx] = 0;
	}
	else if (eap->errmsg == NULL)
	    /* set TRUE, so this conditional will never get active */
	    cstack->cs_flags[cstack->cs_idx] = CSF_TRUE;
    }
    else
	cstack->cs_flags[cstack->cs_idx] |= CSF_ELSE;
}

/*
 * Handle ":while" and ":for".
 */
    void
ex_while(exarg_T *eap)
{
    int		error;
    int		skip;
    int		result;
    struct condstack	*cstack = eap->cstack;

    if (cstack->cs_idx == CSTACK_LEN - 1)
	eap->errmsg = (char_u *)N_("E585: :while/:for nesting too deep");
    else
    {
	/*
	 * The loop flag is set when we have jumped back from the matching
	 * ":endwhile" or ":endfor".  When not set, need to initialise this
	 * cstack entry.
	 */
	if ((cstack->cs_lflags & CSL_HAD_LOOP) == 0)
	{
	    ++cstack->cs_idx;
	    ++cstack->cs_looplevel;
	    cstack->cs_line[cstack->cs_idx] = -1;
	}
	cstack->cs_flags[cstack->cs_idx] =
			       eap->cmdidx == CMD_while ? CSF_WHILE : CSF_FOR;

	/*
	 * Don't do something after an error, interrupt, or throw, or when
	 * there is a surrounding conditional and it was not active.
	 */
	skip = did_emsg || got_int || did_throw || (cstack->cs_idx > 0
		&& !(cstack->cs_flags[cstack->cs_idx - 1] & CSF_ACTIVE));
	if (eap->cmdidx == CMD_while)
	{
	    /*
	     * ":while bool-expr"
	     */
	    result = eval_to_bool(eap->arg, &error, &eap->nextcmd, skip);
	}
	else
	{
	    void *fi;

	    /*
	     * ":for var in list-expr"
	     */
	    if ((cstack->cs_lflags & CSL_HAD_LOOP) != 0)
	    {
		/* Jumping here from a ":continue" or ":endfor": use the
		 * previously evaluated list. */
		fi = cstack->cs_forinfo[cstack->cs_idx];
		error = FALSE;
	    }
	    else
	    {
		/* Evaluate the argument and get the info in a structure. */
		fi = eval_for_line(eap->arg, &error, &eap->nextcmd, skip);
		cstack->cs_forinfo[cstack->cs_idx] = fi;
	    }

	    /* use the element at the start of the list and advance */
	    if (!error && fi != NULL && !skip)
		result = next_for_item(fi, eap->arg);
	    else
		result = FALSE;

	    if (!result)
	    {
		free_for_info(fi);
		cstack->cs_forinfo[cstack->cs_idx] = NULL;
	    }
	}

	/*
	 * If this cstack entry was just initialised and is active, set the
	 * loop flag, so do_cmdline() will set the line number in cs_line[].
	 * If executing the command a second time, clear the loop flag.
	 */
	if (!skip && !error && result)
	{
	    cstack->cs_flags[cstack->cs_idx] |= (CSF_ACTIVE | CSF_TRUE);
	    cstack->cs_lflags ^= CSL_HAD_LOOP;
	}
	else
	{
	    cstack->cs_lflags &= ~CSL_HAD_LOOP;
	    /* If the ":while" evaluates to FALSE or ":for" is past the end of
	     * the list, show the debug prompt at the ":endwhile"/":endfor" as
	     * if there was a ":break" in a ":while"/":for" evaluating to
	     * TRUE. */
	    if (!skip && !error)
		cstack->cs_flags[cstack->cs_idx] |= CSF_TRUE;
	}
    }
}

/*
 * ":continue"
 */
    void
ex_continue(exarg_T *eap)
{
    int		idx;
    struct condstack	*cstack = eap->cstack;

    if (cstack->cs_looplevel <= 0 || cstack->cs_idx < 0)
	eap->errmsg = (char_u *)N_("E586: :continue without :while or :for");
    else
    {
	/* Try to find the matching ":while".  This might stop at a try
	 * conditional not in its finally clause (which is then to be executed
	 * next).  Therefor, inactivate all conditionals except the ":while"
	 * itself (if reached). */
	idx = cleanup_conditionals(cstack, CSF_WHILE | CSF_FOR, FALSE);
	if (idx >= 0 && (cstack->cs_flags[idx] & (CSF_WHILE | CSF_FOR)))
	{
	    rewind_conditionals(cstack, idx, CSF_TRY, &cstack->cs_trylevel);

	    /*
	     * Set CSL_HAD_CONT, so do_cmdline() will jump back to the
	     * matching ":while".
	     */
	    cstack->cs_lflags |= CSL_HAD_CONT;	/* let do_cmdline() handle it */
	}
	else
	{
	    /* If a try conditional not in its finally clause is reached first,
	     * make the ":continue" pending for execution at the ":endtry". */
	    cstack->cs_pending[idx] = CSTP_CONTINUE;
	    report_make_pending(CSTP_CONTINUE, NULL);
	}
    }
}

/*
 * ":break"
 */
    void
ex_break(exarg_T *eap)
{
    int		idx;
    struct condstack	*cstack = eap->cstack;

    if (cstack->cs_looplevel <= 0 || cstack->cs_idx < 0)
	eap->errmsg = (char_u *)N_("E587: :break without :while or :for");
    else
    {
	/* Inactivate conditionals until the matching ":while" or a try
	 * conditional not in its finally clause (which is then to be
	 * executed next) is found.  In the latter case, make the ":break"
	 * pending for execution at the ":endtry". */
	idx = cleanup_conditionals(cstack, CSF_WHILE | CSF_FOR, TRUE);
	if (idx >= 0 && !(cstack->cs_flags[idx] & (CSF_WHILE | CSF_FOR)))
	{
	    cstack->cs_pending[idx] = CSTP_BREAK;
	    report_make_pending(CSTP_BREAK, NULL);
	}
    }
}

/*
 * ":endwhile" and ":endfor"
 */
    void
ex_endwhile(exarg_T *eap)
{
    struct condstack	*cstack = eap->cstack;
    int			idx;
    char_u		*err;
    int			csf;
    int			fl;

    if (eap->cmdidx == CMD_endwhile)
    {
	err = e_while;
	csf = CSF_WHILE;
    }
    else
    {
	err = e_for;
	csf = CSF_FOR;
    }

    if (cstack->cs_looplevel <= 0 || cstack->cs_idx < 0)
	eap->errmsg = err;
    else
    {
	fl =  cstack->cs_flags[cstack->cs_idx];
	if (!(fl & csf))
	{
	    /* If we are in a ":while" or ":for" but used the wrong endloop
	     * command, do not rewind to the next enclosing ":for"/":while". */
	    if (fl & CSF_WHILE)
		eap->errmsg = (char_u *)_("E732: Using :endfor with :while");
	    else if (fl & CSF_FOR)
		eap->errmsg = (char_u *)_("E733: Using :endwhile with :for");
	}
	if (!(fl & (CSF_WHILE | CSF_FOR)))
	{
	    if (!(fl & CSF_TRY))
		eap->errmsg = e_endif;
	    else if (fl & CSF_FINALLY)
		eap->errmsg = e_endtry;
	    /* Try to find the matching ":while" and report what's missing. */
	    for (idx = cstack->cs_idx; idx > 0; --idx)
	    {
		fl =  cstack->cs_flags[idx];
		if ((fl & CSF_TRY) && !(fl & CSF_FINALLY))
		{
		    /* Give up at a try conditional not in its finally clause.
		     * Ignore the ":endwhile"/":endfor". */
		    eap->errmsg = err;
		    return;
		}
		if (fl & csf)
		    break;
	    }
	    /* Cleanup and rewind all contained (and unclosed) conditionals. */
	    (void)cleanup_conditionals(cstack, CSF_WHILE | CSF_FOR, FALSE);
	    rewind_conditionals(cstack, idx, CSF_TRY, &cstack->cs_trylevel);
	}

	/*
	 * When debugging or a breakpoint was encountered, display the debug
	 * prompt (if not already done).  This shows the user that an
	 * ":endwhile"/":endfor" is executed when the ":while" was not TRUE or
	 * after a ":break".  Handle a ">quit" debug command as if an
	 * interrupt had occurred before the ":endwhile"/":endfor".  That is,
	 * throw an interrupt exception if appropriate.  Doing this here
	 * prevents that an exception for a parsing error is discarded when
	 * throwing the interrupt exception later on.
	 */
	else if (cstack->cs_flags[cstack->cs_idx] & CSF_TRUE
		&& !(cstack->cs_flags[cstack->cs_idx] & CSF_ACTIVE)
		&& dbg_check_skipped(eap))
	    (void)do_intthrow(cstack);

	/*
	 * Set loop flag, so do_cmdline() will jump back to the matching
	 * ":while" or ":for".
	 */
	cstack->cs_lflags |= CSL_HAD_ENDLOOP;
    }
}


/*
 * ":throw expr"
 */
    void
ex_throw(exarg_T *eap)
{
    char_u	*arg = eap->arg;
    char_u	*value;

    if (*arg != NUL && *arg != '|' && *arg != '\n')
	value = eval_to_string_skip(arg, &eap->nextcmd, eap->skip);
    else
    {
	EMSG(_(e_argreq));
	value = NULL;
    }

    /* On error or when an exception is thrown during argument evaluation, do
     * not throw. */
    if (!eap->skip && value != NULL)
    {
	if (throw_exception(value, ET_USER, NULL) == FAIL)
	    vim_free(value);
	else
	    do_throw(eap->cstack);
    }
}

/*
 * Throw the current exception through the specified cstack.  Common routine
 * for ":throw" (user exception) and error and interrupt exceptions.  Also
 * used for rethrowing an uncaught exception.
 */
    void
do_throw(struct condstack *cstack)
{
    int		idx;
    int		inactivate_try = FALSE;

    /*
     * Cleanup and inactivate up to the next surrounding try conditional that
     * is not in its finally clause.  Normally, do not inactivate the try
     * conditional itself, so that its ACTIVE flag can be tested below.  But
     * if a previous error or interrupt has not been converted to an exception,
     * inactivate the try conditional, too, as if the conversion had been done,
     * and reset the did_emsg or got_int flag, so this won't happen again at
     * the next surrounding try conditional.
     */
#ifndef THROW_ON_ERROR_TRUE
    if (did_emsg && !THROW_ON_ERROR)
    {
	inactivate_try = TRUE;
	did_emsg = FALSE;
    }
#endif
#ifndef THROW_ON_INTERRUPT_TRUE
    if (got_int && !THROW_ON_INTERRUPT)
    {
	inactivate_try = TRUE;
	got_int = FALSE;
    }
#endif
    idx = cleanup_conditionals(cstack, 0, inactivate_try);
    if (idx >= 0)
    {
	/*
	 * If this try conditional is active and we are before its first
	 * ":catch", set THROWN so that the ":catch" commands will check
	 * whether the exception matches.  When the exception came from any of
	 * the catch clauses, it will be made pending at the ":finally" (if
	 * present) and rethrown at the ":endtry".  This will also happen if
	 * the try conditional is inactive.  This is the case when we are
	 * throwing an exception due to an error or interrupt on the way from
	 * a preceding ":continue", ":break", ":return", ":finish", error or
	 * interrupt (not converted to an exception) to the finally clause or
	 * from a preceding throw of a user or error or interrupt exception to
	 * the matching catch clause or the finally clause.
	 */
	if (!(cstack->cs_flags[idx] & CSF_CAUGHT))
	{
	    if (cstack->cs_flags[idx] & CSF_ACTIVE)
		cstack->cs_flags[idx] |= CSF_THROWN;
	    else
		/* THROWN may have already been set for a catchable exception
		 * that has been discarded.  Ensure it is reset for the new
		 * exception. */
		cstack->cs_flags[idx] &= ~CSF_THROWN;
	}
	cstack->cs_flags[idx] &= ~CSF_ACTIVE;
	cstack->cs_exception[idx] = current_exception;
    }
#if 0
    /* TODO: Add optimization below.  Not yet done because of interface
     * problems to eval.c and ex_cmds2.c. (Servatius) */
    else
    {
	/*
	 * There are no catch clauses to check or finally clauses to execute.
	 * End the current script or function.  The exception will be rethrown
	 * in the caller.
	 */
	if (getline_equal(eap->getline, eap->cookie, get_func_line))
	    current_funccal->returned = TRUE;
	elseif (eap->get_func_line == getsourceline)
	    ((struct source_cookie *)eap->cookie)->finished = TRUE;
    }
#endif

    did_throw = TRUE;
}

/*
 * ":try"
 */
    void
ex_try(exarg_T *eap)
{
    int		skip;
    struct condstack	*cstack = eap->cstack;

    if (cstack->cs_idx == CSTACK_LEN - 1)
	eap->errmsg = (char_u *)N_("E601: :try nesting too deep");
    else
    {
	++cstack->cs_idx;
	++cstack->cs_trylevel;
	cstack->cs_flags[cstack->cs_idx] = CSF_TRY;
	cstack->cs_pending[cstack->cs_idx] = CSTP_NONE;

	/*
	 * Don't do something after an error, interrupt, or throw, or when there
	 * is a surrounding conditional and it was not active.
	 */
	skip = did_emsg || got_int || did_throw || (cstack->cs_idx > 0
		&& !(cstack->cs_flags[cstack->cs_idx - 1] & CSF_ACTIVE));

	if (!skip)
	{
	    /* Set ACTIVE and TRUE.  TRUE means that the corresponding ":catch"
	     * commands should check for a match if an exception is thrown and
	     * that the finally clause needs to be executed. */
	    cstack->cs_flags[cstack->cs_idx] |= CSF_ACTIVE | CSF_TRUE;

	    /*
	     * ":silent!", even when used in a try conditional, disables
	     * displaying of error messages and conversion of errors to
	     * exceptions.  When the silent commands again open a try
	     * conditional, save "emsg_silent" and reset it so that errors are
	     * again converted to exceptions.  The value is restored when that
	     * try conditional is left.  If it is left normally, the commands
	     * following the ":endtry" are again silent.  If it is left by
	     * a ":continue", ":break", ":return", or ":finish", the commands
	     * executed next are again silent.  If it is left due to an
	     * aborting error, an interrupt, or an exception, restoring
	     * "emsg_silent" does not matter since we are already in the
	     * aborting state and/or the exception has already been thrown.
	     * The effect is then just freeing the memory that was allocated
	     * to save the value.
	     */
	    if (emsg_silent)
	    {
		eslist_T	*elem;

		elem = (eslist_T *)alloc((unsigned)sizeof(struct eslist_elem));
		if (elem == NULL)
		    EMSG(_(e_outofmem));
		else
		{
		    elem->saved_emsg_silent = emsg_silent;
		    elem->next = cstack->cs_emsg_silent_list;
		    cstack->cs_emsg_silent_list = elem;
		    cstack->cs_flags[cstack->cs_idx] |= CSF_SILENT;
		    emsg_silent = 0;
		}
	    }
	}

    }
}

/*
 * ":catch /{pattern}/" and ":catch"
 */
    void
ex_catch(exarg_T *eap)
{
    int		idx = 0;
    int		give_up = FALSE;
    int		skip = FALSE;
    int		caught = FALSE;
    char_u	*end;
    int		save_char = 0;
    char_u	*save_cpo;
    regmatch_T	regmatch;
    int		prev_got_int;
    struct condstack	*cstack = eap->cstack;
    char_u	*pat;

    if (cstack->cs_trylevel <= 0 || cstack->cs_idx < 0)
    {
	eap->errmsg = (char_u *)N_("E603: :catch without :try");
	give_up = TRUE;
    }
    else
    {
	if (!(cstack->cs_flags[cstack->cs_idx] & CSF_TRY))
	{
	    /* Report what's missing if the matching ":try" is not in its
	     * finally clause. */
	    eap->errmsg = get_end_emsg(cstack);
	    skip = TRUE;
	}
	for (idx = cstack->cs_idx; idx > 0; --idx)
	    if (cstack->cs_flags[idx] & CSF_TRY)
		break;
	if (cstack->cs_flags[idx] & CSF_FINALLY)
	{
	    /* Give up for a ":catch" after ":finally" and ignore it.
	     * Just parse. */
	    eap->errmsg = (char_u *)N_("E604: :catch after :finally");
	    give_up = TRUE;
	}
	else
	    rewind_conditionals(cstack, idx, CSF_WHILE | CSF_FOR,
						       &cstack->cs_looplevel);
    }

    if (ends_excmd(*eap->arg))	/* no argument, catch all errors */
    {
	pat = (char_u *)".*";
	end = NULL;
	eap->nextcmd = find_nextcmd(eap->arg);
    }
    else
    {
	pat = eap->arg + 1;
	end = skip_regexp(pat, *eap->arg, TRUE, NULL);
    }

    if (!give_up)
    {
	/*
	 * Don't do something when no exception has been thrown or when the
	 * corresponding try block never got active (because of an inactive
	 * surrounding conditional or after an error or interrupt or throw).
	 */
	if (!did_throw || !(cstack->cs_flags[idx] & CSF_TRUE))
	    skip = TRUE;

	/*
	 * Check for a match only if an exception is thrown but not caught by
	 * a previous ":catch".  An exception that has replaced a discarded
	 * exception is not checked (THROWN is not set then).
	 */
	if (!skip && (cstack->cs_flags[idx] & CSF_THROWN)
		&& !(cstack->cs_flags[idx] & CSF_CAUGHT))
	{
	    if (end != NULL && *end != NUL && !ends_excmd(*skipwhite(end + 1)))
	    {
		EMSG(_(e_trailing));
		return;
	    }

	    /* When debugging or a breakpoint was encountered, display the
	     * debug prompt (if not already done) before checking for a match.
	     * This is a helpful hint for the user when the regular expression
	     * matching fails.  Handle a ">quit" debug command as if an
	     * interrupt had occurred before the ":catch".  That is, discard
	     * the original exception, replace it by an interrupt exception,
	     * and don't catch it in this try block. */
	    if (!dbg_check_skipped(eap) || !do_intthrow(cstack))
	    {
		/* Terminate the pattern and avoid the 'l' flag in 'cpoptions'
		 * while compiling it. */
		if (end != NULL)
		{
		    save_char = *end;
		    *end = NUL;
		}
		save_cpo  = p_cpo;
		p_cpo = (char_u *)"";
		/* Disable error messages, it will make current_exception
		 * invalid. */
		++emsg_off;
		regmatch.regprog = vim_regcomp(pat, RE_MAGIC + RE_STRING);
		--emsg_off;
		regmatch.rm_ic = FALSE;
		if (end != NULL)
		    *end = save_char;
		p_cpo = save_cpo;
		if (regmatch.regprog == NULL)
		    EMSG2(_(e_invarg2), pat);
		else
		{
		    /*
		     * Save the value of got_int and reset it.  We don't want
		     * a previous interruption cancel matching, only hitting
		     * CTRL-C while matching should abort it.
		     */
		    prev_got_int = got_int;
		    got_int = FALSE;
		    caught = vim_regexec_nl(&regmatch, current_exception->value,
			    (colnr_T)0);
		    got_int |= prev_got_int;
		    vim_regfree(regmatch.regprog);
		}
	    }
	}

	if (caught)
	{
	    /* Make this ":catch" clause active and reset did_emsg, got_int,
	     * and did_throw.  Put the exception on the caught stack. */
	    cstack->cs_flags[idx] |= CSF_ACTIVE | CSF_CAUGHT;
	    did_emsg = got_int = did_throw = FALSE;
	    catch_exception((except_T *)cstack->cs_exception[idx]);
	    /* It's mandatory that the current exception is stored in the cstack
	     * so that it can be discarded at the next ":catch", ":finally", or
	     * ":endtry" or when the catch clause is left by a ":continue",
	     * ":break", ":return", ":finish", error, interrupt, or another
	     * exception. */
	    if (cstack->cs_exception[cstack->cs_idx] != current_exception)
		internal_error("ex_catch()");
	}
	else
	{
	    /*
	     * If there is a preceding catch clause and it caught the exception,
	     * finish the exception now.  This happens also after errors except
	     * when this ":catch" was after the ":finally" or not within
	     * a ":try".  Make the try conditional inactive so that the
	     * following catch clauses are skipped.  On an error or interrupt
	     * after the preceding try block or catch clause was left by
	     * a ":continue", ":break", ":return", or ":finish", discard the
	     * pending action.
	     */
	    cleanup_conditionals(cstack, CSF_TRY, TRUE);
	}
    }

    if (end != NULL)
	eap->nextcmd = find_nextcmd(end);
}

/*
 * ":finally"
 */
    void
ex_finally(exarg_T *eap)
{
    int		idx;
    int		skip = FALSE;
    int		pending = CSTP_NONE;
    struct condstack	*cstack = eap->cstack;

    if (cstack->cs_trylevel <= 0 || cstack->cs_idx < 0)
	eap->errmsg = (char_u *)N_("E606: :finally without :try");
    else
    {
	if (!(cstack->cs_flags[cstack->cs_idx] & CSF_TRY))
	{
	    eap->errmsg = get_end_emsg(cstack);
	    for (idx = cstack->cs_idx - 1; idx > 0; --idx)
		if (cstack->cs_flags[idx] & CSF_TRY)
		    break;
	    /* Make this error pending, so that the commands in the following
	     * finally clause can be executed.  This overrules also a pending
	     * ":continue", ":break", ":return", or ":finish". */
	    pending = CSTP_ERROR;
	}
	else
	    idx = cstack->cs_idx;

	if (cstack->cs_flags[idx] & CSF_FINALLY)
	{
	    /* Give up for a multiple ":finally" and ignore it. */
	    eap->errmsg = (char_u *)N_("E607: multiple :finally");
	    return;
	}
	rewind_conditionals(cstack, idx, CSF_WHILE | CSF_FOR,
						       &cstack->cs_looplevel);

	/*
	 * Don't do something when the corresponding try block never got active
	 * (because of an inactive surrounding conditional or after an error or
	 * interrupt or throw) or for a ":finally" without ":try" or a multiple
	 * ":finally".  After every other error (did_emsg or the conditional
	 * errors detected above) or after an interrupt (got_int) or an
	 * exception (did_throw), the finally clause must be executed.
	 */
	skip = !(cstack->cs_flags[cstack->cs_idx] & CSF_TRUE);

	if (!skip)
	{
	    /* When debugging or a breakpoint was encountered, display the
	     * debug prompt (if not already done).  The user then knows that the
	     * finally clause is executed. */
	    if (dbg_check_skipped(eap))
	    {
		/* Handle a ">quit" debug command as if an interrupt had
		 * occurred before the ":finally".  That is, discard the
		 * original exception and replace it by an interrupt
		 * exception. */
		(void)do_intthrow(cstack);
	    }

	    /*
	     * If there is a preceding catch clause and it caught the exception,
	     * finish the exception now.  This happens also after errors except
	     * when this is a multiple ":finally" or one not within a ":try".
	     * After an error or interrupt, this also discards a pending
	     * ":continue", ":break", ":finish", or ":return" from the preceding
	     * try block or catch clause.
	     */
	    cleanup_conditionals(cstack, CSF_TRY, FALSE);

	    /*
	     * Make did_emsg, got_int, did_throw pending.  If set, they overrule
	     * a pending ":continue", ":break", ":return", or ":finish".  Then
	     * we have particularly to discard a pending return value (as done
	     * by the call to cleanup_conditionals() above when did_emsg or
	     * got_int is set).  The pending values are restored by the
	     * ":endtry", except if there is a new error, interrupt, exception,
	     * ":continue", ":break", ":return", or ":finish" in the following
	     * finally clause.  A missing ":endwhile", ":endfor" or ":endif"
	     * detected here is treated as if did_emsg and did_throw had
	     * already been set, respectively in case that the error is not
	     * converted to an exception, did_throw had already been unset.
	     * We must not set did_emsg here since that would suppress the
	     * error message.
	     */
	    if (pending == CSTP_ERROR || did_emsg || got_int || did_throw)
	    {
		if (cstack->cs_pending[cstack->cs_idx] == CSTP_RETURN)
		{
		    report_discard_pending(CSTP_RETURN,
					   cstack->cs_rettv[cstack->cs_idx]);
		    discard_pending_return(cstack->cs_rettv[cstack->cs_idx]);
		}
		if (pending == CSTP_ERROR && !did_emsg)
		    pending |= (THROW_ON_ERROR) ? CSTP_THROW : 0;
		else
		    pending |= did_throw ? CSTP_THROW : 0;
		pending |= did_emsg  ? CSTP_ERROR     : 0;
		pending |= got_int   ? CSTP_INTERRUPT : 0;
		cstack->cs_pending[cstack->cs_idx] = pending;

		/* It's mandatory that the current exception is stored in the
		 * cstack so that it can be rethrown at the ":endtry" or be
		 * discarded if the finally clause is left by a ":continue",
		 * ":break", ":return", ":finish", error, interrupt, or another
		 * exception.  When emsg() is called for a missing ":endif" or
		 * a missing ":endwhile"/":endfor" detected here, the
		 * exception will be discarded. */
		if (did_throw && cstack->cs_exception[cstack->cs_idx]
							 != current_exception)
		    internal_error("ex_finally()");
	    }

	    /*
	     * Set CSL_HAD_FINA, so do_cmdline() will reset did_emsg,
	     * got_int, and did_throw and make the finally clause active.
	     * This will happen after emsg() has been called for a missing
	     * ":endif" or a missing ":endwhile"/":endfor" detected here, so
	     * that the following finally clause will be executed even then.
	     */
	    cstack->cs_lflags |= CSL_HAD_FINA;
	}
    }
}

/*
 * ":endtry"
 */
    void
ex_endtry(exarg_T *eap)
{
    int		idx;
    int		skip;
    int		rethrow = FALSE;
    int		pending = CSTP_NONE;
    void	*rettv = NULL;
    struct condstack	*cstack = eap->cstack;

    if (cstack->cs_trylevel <= 0 || cstack->cs_idx < 0)
	eap->errmsg = (char_u *)N_("E602: :endtry without :try");
    else
    {
	/*
	 * Don't do something after an error, interrupt or throw in the try
	 * block, catch clause, or finally clause preceding this ":endtry" or
	 * when an error or interrupt occurred after a ":continue", ":break",
	 * ":return", or ":finish" in a try block or catch clause preceding this
	 * ":endtry" or when the try block never got active (because of an
	 * inactive surrounding conditional or after an error or interrupt or
	 * throw) or when there is a surrounding conditional and it has been
	 * made inactive by a ":continue", ":break", ":return", or ":finish" in
	 * the finally clause.  The latter case need not be tested since then
	 * anything pending has already been discarded. */
	skip = did_emsg || got_int || did_throw ||
	    !(cstack->cs_flags[cstack->cs_idx] & CSF_TRUE);

	if (!(cstack->cs_flags[cstack->cs_idx] & CSF_TRY))
	{
	    eap->errmsg = get_end_emsg(cstack);
	    /* Find the matching ":try" and report what's missing. */
	    idx = cstack->cs_idx;
	    do
		--idx;
	    while (idx > 0 && !(cstack->cs_flags[idx] & CSF_TRY));
	    rewind_conditionals(cstack, idx, CSF_WHILE | CSF_FOR,
						       &cstack->cs_looplevel);
	    skip = TRUE;

	    /*
	     * If an exception is being thrown, discard it to prevent it from
	     * being rethrown at the end of this function.  It would be
	     * discarded by the error message, anyway.  Resets did_throw.
	     * This does not affect the script termination due to the error
	     * since "trylevel" is decremented after emsg() has been called.
	     */
	    if (did_throw)
		discard_current_exception();
	}
	else
	{
	    idx = cstack->cs_idx;

	    /*
	     * If we stopped with the exception currently being thrown at this
	     * try conditional since we didn't know that it doesn't have
	     * a finally clause, we need to rethrow it after closing the try
	     * conditional.
	     */
	    if (did_throw && (cstack->cs_flags[idx] & CSF_TRUE)
		    && !(cstack->cs_flags[idx] & CSF_FINALLY))
		rethrow = TRUE;
	}

	/* If there was no finally clause, show the user when debugging or
	 * a breakpoint was encountered that the end of the try conditional has
	 * been reached: display the debug prompt (if not already done).  Do
	 * this on normal control flow or when an exception was thrown, but not
	 * on an interrupt or error not converted to an exception or when
	 * a ":break", ":continue", ":return", or ":finish" is pending.  These
	 * actions are carried out immediately.
	 */
	if ((rethrow || (!skip
			&& !(cstack->cs_flags[idx] & CSF_FINALLY)
			&& !cstack->cs_pending[idx]))
		&& dbg_check_skipped(eap))
	{
	    /* Handle a ">quit" debug command as if an interrupt had occurred
	     * before the ":endtry".  That is, throw an interrupt exception and
	     * set "skip" and "rethrow". */
	    if (got_int)
	    {
		skip = TRUE;
		(void)do_intthrow(cstack);
		/* The do_intthrow() call may have reset did_throw or
		 * cstack->cs_pending[idx].*/
		rethrow = FALSE;
		if (did_throw && !(cstack->cs_flags[idx] & CSF_FINALLY))
		    rethrow = TRUE;
	    }
	}

	/*
	 * If a ":return" is pending, we need to resume it after closing the
	 * try conditional; remember the return value.  If there was a finally
	 * clause making an exception pending, we need to rethrow it.  Make it
	 * the exception currently being thrown.
	 */
	if (!skip)
	{
	    pending = cstack->cs_pending[idx];
	    cstack->cs_pending[idx] = CSTP_NONE;
	    if (pending == CSTP_RETURN)
		rettv = cstack->cs_rettv[idx];
	    else if (pending & CSTP_THROW)
		current_exception = cstack->cs_exception[idx];
	}

	/*
	 * Discard anything pending on an error, interrupt, or throw in the
	 * finally clause.  If there was no ":finally", discard a pending
	 * ":continue", ":break", ":return", or ":finish" if an error or
	 * interrupt occurred afterwards, but before the ":endtry" was reached.
	 * If an exception was caught by the last of the catch clauses and there
	 * was no finally clause, finish the exception now.  This happens also
	 * after errors except when this ":endtry" is not within a ":try".
	 * Restore "emsg_silent" if it has been reset by this try conditional.
	 */
	(void)cleanup_conditionals(cstack, CSF_TRY | CSF_SILENT, TRUE);

	--cstack->cs_idx;
	--cstack->cs_trylevel;

	if (!skip)
	{
	    report_resume_pending(pending,
		    (pending == CSTP_RETURN) ? rettv :
		    (pending & CSTP_THROW) ? (void *)current_exception : NULL);
	    switch (pending)
	    {
		case CSTP_NONE:
		    break;

		/* Reactivate a pending ":continue", ":break", ":return",
		 * ":finish" from the try block or a catch clause of this try
		 * conditional.  This is skipped, if there was an error in an
		 * (unskipped) conditional command or an interrupt afterwards
		 * or if the finally clause is present and executed a new error,
		 * interrupt, throw, ":continue", ":break", ":return", or
		 * ":finish". */
		case CSTP_CONTINUE:
		    ex_continue(eap);
		    break;
		case CSTP_BREAK:
		    ex_break(eap);
		    break;
		case CSTP_RETURN:
		    do_return(eap, FALSE, FALSE, rettv);
		    break;
		case CSTP_FINISH:
		    do_finish(eap, FALSE);
		    break;

		/* When the finally clause was entered due to an error,
		 * interrupt or throw (as opposed to a ":continue", ":break",
		 * ":return", or ":finish"), restore the pending values of
		 * did_emsg, got_int, and did_throw.  This is skipped, if there
		 * was a new error, interrupt, throw, ":continue", ":break",
		 * ":return", or ":finish".  in the finally clause. */
		default:
		    if (pending & CSTP_ERROR)
			did_emsg = TRUE;
		    if (pending & CSTP_INTERRUPT)
			got_int = TRUE;
		    if (pending & CSTP_THROW)
			rethrow = TRUE;
		    break;
	    }
	}

	if (rethrow)
	    /* Rethrow the current exception (within this cstack). */
	    do_throw(cstack);
    }
}

/*
 * enter_cleanup() and leave_cleanup()
 *
 * Functions to be called before/after invoking a sequence of autocommands for
 * cleanup for a failed command.  (Failure means here that a call to emsg()
 * has been made, an interrupt occurred, or there is an uncaught exception
 * from a previous autocommand execution of the same command.)
 *
 * Call enter_cleanup() with a pointer to a cleanup_T and pass the same
 * pointer to leave_cleanup().  The cleanup_T structure stores the pending
 * error/interrupt/exception state.
 */

/*
 * This function works a bit like ex_finally() except that there was not
 * actually an extra try block around the part that failed and an error or
 * interrupt has not (yet) been converted to an exception.  This function
 * saves the error/interrupt/ exception state and prepares for the call to
 * do_cmdline() that is going to be made for the cleanup autocommand
 * execution.
 */
    void
enter_cleanup(cleanup_T *csp)
{
    int		pending = CSTP_NONE;

    /*
     * Postpone did_emsg, got_int, did_throw.  The pending values will be
     * restored by leave_cleanup() except if there was an aborting error,
     * interrupt, or uncaught exception after this function ends.
     */
    if (did_emsg || got_int || did_throw || need_rethrow)
    {
	csp->pending = (did_emsg     ? CSTP_ERROR     : 0)
		     | (got_int      ? CSTP_INTERRUPT : 0)
		     | (did_throw    ? CSTP_THROW     : 0)
		     | (need_rethrow ? CSTP_THROW     : 0);

	/* If we are currently throwing an exception (did_throw), save it as
	 * well.  On an error not yet converted to an exception, update
	 * "force_abort" and reset "cause_abort" (as do_errthrow() would do).
	 * This is needed for the do_cmdline() call that is going to be made
	 * for autocommand execution.  We need not save *msg_list because
	 * there is an extra instance for every call of do_cmdline(), anyway.
	 */
	if (did_throw || need_rethrow)
	{
	    csp->exception = current_exception;
	    current_exception = NULL;
	}
	else
	{
	    csp->exception = NULL;
	    if (did_emsg)
	    {
		force_abort |= cause_abort;
		cause_abort = FALSE;
	    }
	}
	did_emsg = got_int = did_throw = need_rethrow = FALSE;

	/* Report if required by the 'verbose' option or when debugging.  */
	report_make_pending(pending, csp->exception);
    }
    else
    {
	csp->pending = CSTP_NONE;
	csp->exception = NULL;
    }
}

/*
 * See comment above enter_cleanup() for how this function is used.
 *
 * This function is a bit like ex_endtry() except that there was not actually
 * an extra try block around the part that failed and an error or interrupt
 * had not (yet) been converted to an exception when the cleanup autocommand
 * sequence was invoked.
 *
 * This function has to be called with the address of the cleanup_T structure
 * filled by enter_cleanup() as an argument; it restores the error/interrupt/
 * exception state saved by that function - except there was an aborting
 * error, an interrupt or an uncaught exception during execution of the
 * cleanup autocommands.  In the latter case, the saved error/interrupt/
 * exception state is discarded.
 */
    void
leave_cleanup(cleanup_T *csp)
{
    int		pending = csp->pending;

    if (pending == CSTP_NONE)	/* nothing to do */
	return;

    /* If there was an aborting error, an interrupt, or an uncaught exception
     * after the corresponding call to enter_cleanup(), discard what has been
     * made pending by it.  Report this to the user if required by the
     * 'verbose' option or when debugging. */
    if (aborting() || need_rethrow)
    {
	if (pending & CSTP_THROW)
	    /* Cancel the pending exception (includes report). */
	    discard_exception((except_T *)csp->exception, FALSE);
	else
	    report_discard_pending(pending, NULL);

	/* If an error was about to be converted to an exception when
	 * enter_cleanup() was called, free the message list. */
	if (msg_list != NULL)
	    free_global_msglist();
    }

    /*
     * If there was no new error, interrupt, or throw between the calls
     * to enter_cleanup() and leave_cleanup(), restore the pending
     * error/interrupt/exception state.
     */
    else
    {
	/*
	 * If there was an exception being thrown when enter_cleanup() was
	 * called, we need to rethrow it.  Make it the exception currently
	 * being thrown.
	 */
	if (pending & CSTP_THROW)
	    current_exception = csp->exception;

	/*
	 * If an error was about to be converted to an exception when
	 * enter_cleanup() was called, let "cause_abort" take the part of
	 * "force_abort" (as done by cause_errthrow()).
	 */
	else if (pending & CSTP_ERROR)
	{
	    cause_abort = force_abort;
	    force_abort = FALSE;
	}

	/*
	 * Restore the pending values of did_emsg, got_int, and did_throw.
	 */
	if (pending & CSTP_ERROR)
	    did_emsg = TRUE;
	if (pending & CSTP_INTERRUPT)
	    got_int = TRUE;
	if (pending & CSTP_THROW)
	    need_rethrow = TRUE;    /* did_throw will be set by do_one_cmd() */

	/* Report if required by the 'verbose' option or when debugging. */
	report_resume_pending(pending,
		   (pending & CSTP_THROW) ? (void *)current_exception : NULL);
    }
}


/*
 * Make conditionals inactive and discard what's pending in finally clauses
 * until the conditional type searched for or a try conditional not in its
 * finally clause is reached.  If this is in an active catch clause, finish
 * the caught exception.
 * Return the cstack index where the search stopped.
 * Values used for "searched_cond" are (CSF_WHILE | CSF_FOR) or CSF_TRY or 0,
 * the latter meaning the innermost try conditional not in its finally clause.
 * "inclusive" tells whether the conditional searched for should be made
 * inactive itself (a try conditional not in its finally clause possibly find
 * before is always made inactive).  If "inclusive" is TRUE and
 * "searched_cond" is CSF_TRY|CSF_SILENT, the saved former value of
 * "emsg_silent", if reset when the try conditional finally reached was
 * entered, is restored (used by ex_endtry()).  This is normally done only
 * when such a try conditional is left.
 */
    int
cleanup_conditionals(
    struct condstack   *cstack,
    int		searched_cond,
    int		inclusive)
{
    int		idx;
    int		stop = FALSE;

    for (idx = cstack->cs_idx; idx >= 0; --idx)
    {
	if (cstack->cs_flags[idx] & CSF_TRY)
	{
	    /*
	     * Discard anything pending in a finally clause and continue the
	     * search.  There may also be a pending ":continue", ":break",
	     * ":return", or ":finish" before the finally clause.  We must not
	     * discard it, unless an error or interrupt occurred afterwards.
	     */
	    if (did_emsg || got_int || (cstack->cs_flags[idx] & CSF_FINALLY))
	    {
		switch (cstack->cs_pending[idx])
		{
		    case CSTP_NONE:
			break;

		    case CSTP_CONTINUE:
		    case CSTP_BREAK:
		    case CSTP_FINISH:
			report_discard_pending(cstack->cs_pending[idx], NULL);
			cstack->cs_pending[idx] = CSTP_NONE;
			break;

		    case CSTP_RETURN:
			report_discard_pending(CSTP_RETURN,
						      cstack->cs_rettv[idx]);
			discard_pending_return(cstack->cs_rettv[idx]);
			cstack->cs_pending[idx] = CSTP_NONE;
			break;

		    default:
			if (cstack->cs_flags[idx] & CSF_FINALLY)
			{
			    if (cstack->cs_pending[idx] & CSTP_THROW)
			    {
				/* Cancel the pending exception.  This is in the
				 * finally clause, so that the stack of the
				 * caught exceptions is not involved. */
				discard_exception((except_T *)
					cstack->cs_exception[idx],
					FALSE);
			    }
			    else
				report_discard_pending(cstack->cs_pending[idx],
					NULL);
			    cstack->cs_pending[idx] = CSTP_NONE;
			}
			break;
		}
	    }

	    /*
	     * Stop at a try conditional not in its finally clause.  If this try
	     * conditional is in an active catch clause, finish the caught
	     * exception.
	     */
	    if (!(cstack->cs_flags[idx] & CSF_FINALLY))
	    {
		if ((cstack->cs_flags[idx] & CSF_ACTIVE)
			&& (cstack->cs_flags[idx] & CSF_CAUGHT))
		    finish_exception((except_T *)cstack->cs_exception[idx]);
		/* Stop at this try conditional - except the try block never
		 * got active (because of an inactive surrounding conditional
		 * or when the ":try" appeared after an error or interrupt or
		 * throw). */
		if (cstack->cs_flags[idx] & CSF_TRUE)
		{
		    if (searched_cond == 0 && !inclusive)
			break;
		    stop = TRUE;
		}
	    }
	}

	/* Stop on the searched conditional type (even when the surrounding
	 * conditional is not active or something has been made pending).
	 * If "inclusive" is TRUE and "searched_cond" is CSF_TRY|CSF_SILENT,
	 * check first whether "emsg_silent" needs to be restored. */
	if (cstack->cs_flags[idx] & searched_cond)
	{
	    if (!inclusive)
		break;
	    stop = TRUE;
	}
	cstack->cs_flags[idx] &= ~CSF_ACTIVE;
	if (stop && searched_cond != (CSF_TRY | CSF_SILENT))
	    break;

	/*
	 * When leaving a try conditional that reset "emsg_silent" on its
	 * entry after saving the original value, restore that value here and
	 * free the memory used to store it.
	 */
	if ((cstack->cs_flags[idx] & CSF_TRY)
		&& (cstack->cs_flags[idx] & CSF_SILENT))
	{
	    eslist_T	*elem;

	    elem = cstack->cs_emsg_silent_list;
	    cstack->cs_emsg_silent_list = elem->next;
	    emsg_silent = elem->saved_emsg_silent;
	    vim_free(elem);
	    cstack->cs_flags[idx] &= ~CSF_SILENT;
	}
	if (stop)
	    break;
    }
    return idx;
}

/*
 * Return an appropriate error message for a missing endwhile/endfor/endif.
 */
   static char_u *
get_end_emsg(struct condstack *cstack)
{
    if (cstack->cs_flags[cstack->cs_idx] & CSF_WHILE)
	return e_endwhile;
    if (cstack->cs_flags[cstack->cs_idx] & CSF_FOR)
	return e_endfor;
    return e_endif;
}


/*
 * Rewind conditionals until index "idx" is reached.  "cond_type" and
 * "cond_level" specify a conditional type and the address of a level variable
 * which is to be decremented with each skipped conditional of the specified
 * type.
 * Also free "for info" structures where needed.
 */
    void
rewind_conditionals(
    struct condstack   *cstack,
    int		idx,
    int		cond_type,
    int		*cond_level)
{
    while (cstack->cs_idx > idx)
    {
	if (cstack->cs_flags[cstack->cs_idx] & cond_type)
	    --*cond_level;
	if (cstack->cs_flags[cstack->cs_idx] & CSF_FOR)
	    free_for_info(cstack->cs_forinfo[cstack->cs_idx]);
	--cstack->cs_idx;
    }
}

/*
 * ":endfunction" when not after a ":function"
 */
    void
ex_endfunction(exarg_T *eap UNUSED)
{
    EMSG(_("E193: :endfunction not inside a function"));
}

/*
 * Return TRUE if the string "p" looks like a ":while" or ":for" command.
 */
    int
has_loop_cmd(char_u *p)
{
    int		len;

    /* skip modifiers, white space and ':' */
    for (;;)
    {
	while (*p == ' ' || *p == '\t' || *p == ':')
	    ++p;
	len = modifier_len(p);
	if (len == 0)
	    break;
	p += len;
    }
    if ((p[0] == 'w' && p[1] == 'h')
	    || (p[0] == 'f' && p[1] == 'o' && p[2] == 'r'))
	return TRUE;
    return FALSE;
}

#endif /* FEAT_EVAL */
