diff options
Diffstat (limited to 'src/vim9execute.c')
-rw-r--r-- | src/vim9execute.c | 54 |
1 files changed, 54 insertions, 0 deletions
diff --git a/src/vim9execute.c b/src/vim9execute.c index 7462b68c9..e92af22cc 100644 --- a/src/vim9execute.c +++ b/src/vim9execute.c @@ -2114,6 +2114,35 @@ call_def_function( } break; + case ISN_SLICE: + { + list_T *list; + int count = iptr->isn_arg.number; + + tv = STACK_TV_BOT(-1); + if (tv->v_type != VAR_LIST) + { + emsg(_(e_listreq)); + goto failed; + } + list = tv->vval.v_list; + + // no error for short list, expect it to be checked earlier + if (list != NULL && list->lv_len >= count) + { + list_T *newlist = list_slice(list, + count, list->lv_len - 1); + + if (newlist != NULL) + { + list_unref(list); + tv->vval.v_list = newlist; + ++newlist->lv_refcount; + } + } + } + break; + case ISN_GETITEM: { listitem_T *li; @@ -2243,6 +2272,25 @@ call_def_function( } break; + case ISN_CHECKLEN: + { + int min_len = iptr->isn_arg.checklen.cl_min_len; + list_T *list = NULL; + + tv = STACK_TV_BOT(-1); + if (tv->v_type == VAR_LIST) + list = tv->vval.v_list; + if (list == NULL || list->lv_len < min_len + || (list->lv_len > min_len + && !iptr->isn_arg.checklen.cl_more_OK)) + { + semsg(_("E1093: Expected %d items but got %d"), + min_len, list == NULL ? 0 : list->lv_len); + goto failed; + } + } + break; + case ISN_2BOOL: { int n; @@ -2814,6 +2862,8 @@ ex_disassemble(exarg_T *eap) // expression operations case ISN_CONCAT: smsg("%4d CONCAT", current); break; case ISN_INDEX: smsg("%4d INDEX", current); break; + case ISN_SLICE: smsg("%4d SLICE %lld", + current, iptr->isn_arg.number); break; case ISN_GETITEM: smsg("%4d ITEM %lld", current, iptr->isn_arg.number); break; case ISN_MEMBER: smsg("%4d MEMBER", current); break; @@ -2826,6 +2876,10 @@ ex_disassemble(exarg_T *eap) vartype_name(iptr->isn_arg.type.ct_type), iptr->isn_arg.type.ct_off); break; + case ISN_CHECKLEN: smsg("%4d CHECKLEN %s%d", current, + iptr->isn_arg.checklen.cl_more_OK ? ">= " : "", + iptr->isn_arg.checklen.cl_min_len); + break; case ISN_2BOOL: if (iptr->isn_arg.number) smsg("%4d INVERT (!val)", current); else |