aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorzeertzjq <zeertzjq@outlook.com>2023-05-05 20:05:18 +0800
committerGitHub <noreply@github.com>2023-05-05 20:05:18 +0800
commitc14aa66cce679e6ff4343401e448d47413660b0c (patch)
treee1f359d22125f4b6c046d66b2595a70db7989ef2 /src
parentd9f0d2da4d29847542072099f103e7248fcacaab (diff)
parentc11417b3d74f02568e37ea3370a7c24141d4f18a (diff)
downloadrneovim-c14aa66cce679e6ff4343401e448d47413660b0c.tar.gz
rneovim-c14aa66cce679e6ff4343401e448d47413660b0c.tar.bz2
rneovim-c14aa66cce679e6ff4343401e448d47413660b0c.zip
Merge pull request #23487 from zeertzjq/vim-8.2.1953
vim-patch:8.2.1953,9.0.{0213,0404,0543,0846,0854,1507}: assert fixes
Diffstat (limited to 'src')
-rw-r--r--src/nvim/eval.h10
-rw-r--r--src/nvim/eval/typval.c4
-rw-r--r--src/nvim/testing.c65
3 files changed, 47 insertions, 32 deletions
diff --git a/src/nvim/eval.h b/src/nvim/eval.h
index e9cdb108a8..5fbfc4702c 100644
--- a/src/nvim/eval.h
+++ b/src/nvim/eval.h
@@ -229,16 +229,6 @@ typedef struct {
Callback callback;
} timer_T;
-/// Type of assert_* check being performed
-typedef enum {
- ASSERT_EQUAL,
- ASSERT_NOTEQUAL,
- ASSERT_MATCH,
- ASSERT_NOTMATCH,
- ASSERT_INRANGE,
- ASSERT_OTHER,
-} assert_type_T;
-
/// types for expressions.
typedef enum {
EXPR_UNKNOWN = 0,
diff --git a/src/nvim/eval/typval.c b/src/nvim/eval/typval.c
index 5f0c082ada..5755178b18 100644
--- a/src/nvim/eval/typval.c
+++ b/src/nvim/eval/typval.c
@@ -56,6 +56,8 @@ static const char e_list_required_for_argument_nr[]
= N_("E1211: List required for argument %d");
static const char e_bool_required_for_argument_nr[]
= N_("E1212: Bool required for argument %d");
+static const char e_float_or_number_required_for_argument_nr[]
+ = N_("E1219: Float or Number required for argument %d");
static const char e_string_or_number_required_for_argument_nr[]
= N_("E1220: String or Number required for argument %d");
static const char e_string_or_list_required_for_argument_nr[]
@@ -4171,7 +4173,7 @@ int tv_check_for_float_or_nr_arg(const typval_T *const args, const int idx)
FUNC_ATTR_NONNULL_ALL FUNC_ATTR_WARN_UNUSED_RESULT FUNC_ATTR_PURE
{
if (args[idx].v_type != VAR_FLOAT && args[idx].v_type != VAR_NUMBER) {
- semsg(_(e_number_required_for_argument_nr), idx + 1);
+ semsg(_(e_float_or_number_required_for_argument_nr), idx + 1);
return FAIL;
}
return OK;
diff --git a/src/nvim/testing.c b/src/nvim/testing.c
index 867a8ffd3a..430d6713ff 100644
--- a/src/nvim/testing.c
+++ b/src/nvim/testing.c
@@ -30,6 +30,16 @@
#include "nvim/types.h"
#include "nvim/vim.h"
+/// Type of assert_* check being performed
+typedef enum {
+ ASSERT_EQUAL,
+ ASSERT_NOTEQUAL,
+ ASSERT_MATCH,
+ ASSERT_NOTMATCH,
+ ASSERT_FAILS,
+ ASSERT_OTHER,
+} assert_type_T;
+
#ifdef INCLUDE_GENERATED_DECLARATIONS
# include "testing.c.generated.h"
#endif
@@ -142,7 +152,7 @@ static void ga_concat_shorten_esc(garray_T *gap, const char *str)
}
/// Fill "gap" with information about an assert error.
-static void fill_assert_error(garray_T *gap, typval_T *opt_msg_tv, char *exp_str,
+static void fill_assert_error(garray_T *gap, typval_T *opt_msg_tv, const char *exp_str,
typval_T *exp_tv_arg, typval_T *got_tv_arg, assert_type_T atype)
{
char *tofree;
@@ -220,7 +230,13 @@ static void fill_assert_error(garray_T *gap, typval_T *opt_msg_tv, char *exp_str
ga_concat_shorten_esc(gap, tofree);
xfree(tofree);
} else {
+ if (atype == ASSERT_FAILS) {
+ ga_concat(gap, "'");
+ }
ga_concat_shorten_esc(gap, exp_str);
+ if (atype == ASSERT_FAILS) {
+ ga_concat(gap, "'");
+ }
}
if (atype != ASSERT_NOTEQUAL) {
@@ -504,6 +520,7 @@ void f_assert_fails(typval_T *argvars, typval_T *rettv, EvalFuncData fptr)
const int save_trylevel = trylevel;
const int called_emsg_before = called_emsg;
const char *wrong_arg_msg = NULL;
+ char *tofree = NULL;
if (tv_check_for_string_or_number_arg(argvars, 0) == FAIL
|| tv_check_for_opt_string_or_list_arg(argvars, 1) == FAIL
@@ -515,15 +532,19 @@ void f_assert_fails(typval_T *argvars, typval_T *rettv, EvalFuncData fptr)
return;
}
- const char *const cmd = tv_get_string_chk(&argvars[0]);
-
// trylevel must be zero for a ":throw" command to be considered failed
trylevel = 0;
suppress_errthrow = true;
in_assert_fails = true;
no_wait_return++;
+ const char *const cmd = tv_get_string_chk(&argvars[0]);
do_cmdline_cmd(cmd);
+
+ // reset here for any errors reported below
+ trylevel = save_trylevel;
+ suppress_errthrow = false;
+
if (called_emsg == called_emsg_before) {
prepare_assert_error(&ga);
ga_concat(&ga, "command did not fail: ");
@@ -534,6 +555,7 @@ void f_assert_fails(typval_T *argvars, typval_T *rettv, EvalFuncData fptr)
} else if (argvars[1].v_type != VAR_UNKNOWN) {
char buf[NUMBUFLEN];
const char *expected;
+ const char *expected_str = NULL;
bool error_found = false;
int error_found_index = 1;
char *actual = emsg_assert_fails_msg == NULL ? "[unknown]" : emsg_assert_fails_msg;
@@ -549,14 +571,23 @@ void f_assert_fails(typval_T *argvars, typval_T *rettv, EvalFuncData fptr)
}
const typval_T *tv = TV_LIST_ITEM_TV(tv_list_first(list));
expected = tv_get_string_buf_chk(tv, buf);
+ if (expected == NULL) {
+ goto theend;
+ }
if (!pattern_match(expected, actual, false)) {
error_found = true;
+ expected_str = expected;
} else if (tv_list_len(list) == 2) {
+ // make a copy, an error in pattern_match() may free it
+ tofree = actual = xstrdup(get_vim_var_str(VV_ERRMSG));
tv = TV_LIST_ITEM_TV(tv_list_last(list));
- actual = get_vim_var_str(VV_ERRMSG);
expected = tv_get_string_buf_chk(tv, buf);
+ if (expected == NULL) {
+ goto theend;
+ }
if (!pattern_match(expected, actual, false)) {
error_found = true;
+ expected_str = expected;
}
}
} else {
@@ -600,8 +631,8 @@ void f_assert_fails(typval_T *argvars, typval_T *rettv, EvalFuncData fptr)
actual_tv.v_type = VAR_STRING;
actual_tv.vval.v_string = actual;
}
- fill_assert_error(&ga, &argvars[2], NULL,
- &argvars[error_found_index], &actual_tv, ASSERT_OTHER);
+ fill_assert_error(&ga, &argvars[2], expected_str,
+ &argvars[error_found_index], &actual_tv, ASSERT_FAILS);
ga_concat(&ga, ": ");
assert_append_cmd_or_arg(&ga, argvars, cmd);
assert_error(&ga);
@@ -623,6 +654,7 @@ theend:
msg_reset_scroll();
lines_left = Rows;
XFREE_CLEAR(emsg_assert_fails_msg);
+ xfree(tofree);
set_vim_var_string(VV_ERRMSG, NULL, 0);
if (wrong_arg_msg != NULL) {
emsg(_(wrong_arg_msg));
@@ -650,16 +682,9 @@ static int assert_inrange(typval_T *argvars)
if (factual < flower || factual > fupper) {
garray_T ga;
prepare_assert_error(&ga);
- if (argvars[3].v_type != VAR_UNKNOWN) {
- char *const tofree = encode_tv2string(&argvars[3], NULL);
- ga_concat(&ga, tofree);
- xfree(tofree);
- } else {
- char msg[80];
- vim_snprintf(msg, sizeof(msg), "Expected range %g - %g, but got %g",
- flower, fupper, factual);
- ga_concat(&ga, msg);
- }
+ char expected_str[200];
+ vim_snprintf(expected_str, sizeof(expected_str), "range %g - %g,", flower, fupper);
+ fill_assert_error(&ga, &argvars[3], expected_str, NULL, &argvars[2], ASSERT_OTHER);
assert_error(&ga);
ga_clear(&ga);
return 1;
@@ -675,13 +700,11 @@ static int assert_inrange(typval_T *argvars)
if (actual < lower || actual > upper) {
garray_T ga;
prepare_assert_error(&ga);
-
- char msg[55];
- vim_snprintf(msg, sizeof(msg),
+ char expected_str[200];
+ vim_snprintf(expected_str, sizeof(expected_str),
"range %" PRIdVARNUMBER " - %" PRIdVARNUMBER ",",
lower, upper); // -V576
- fill_assert_error(&ga, &argvars[3], msg, NULL, &argvars[2],
- ASSERT_INRANGE);
+ fill_assert_error(&ga, &argvars[3], expected_str, NULL, &argvars[2], ASSERT_OTHER);
assert_error(&ga);
ga_clear(&ga);
return 1;