diff options
author | Bram Moolenaar <Bram@vim.org> | 2023-01-04 18:54:09 +0000 |
---|---|---|
committer | Bram Moolenaar <Bram@vim.org> | 2023-01-04 18:54:09 +0000 |
commit | 3259ff3b3bd152d61c1cef7901023034c0d655a3 (patch) | |
tree | fd0aa894a0ba56586ee392eb69ee98e4b3a3d954 | |
parent | c8b204952f0452fe1276d30ae6a5d38a3f421b95 (diff) | |
download | vim-git-3259ff3b3bd152d61c1cef7901023034c0d655a3.tar.gz |
patch 9.0.1147: cannot access a class member in a compiled functionv9.0.1147
Problem: Cannot access a class member in a compiled function.
Solution: Implement looking up a class member.
-rw-r--r-- | src/testdir/test_vim9_class.vim | 5 | ||||
-rw-r--r-- | src/version.c | 2 | ||||
-rw-r--r-- | src/vim9expr.c | 49 |
3 files changed, 38 insertions, 18 deletions
diff --git a/src/testdir/test_vim9_class.vim b/src/testdir/test_vim9_class.vim index 60730c4d5..a55671bcb 100644 --- a/src/testdir/test_vim9_class.vim +++ b/src/testdir/test_vim9_class.vim @@ -439,6 +439,11 @@ def Test_class_member() TextPos.AddToCounter(3) assert_equal(3, TextPos.counter) assert_fails('echo TextPos.noSuchMember', 'E1338:') + + def GetCounter(): number + return TextPos.counter + enddef + assert_equal(3, GetCounter()) assert_fails('TextPos.noSuchMember = 2', 'E1337:') assert_fails('TextPos.counter = 5', 'E1335:') diff --git a/src/version.c b/src/version.c index 44d8db9b0..39f7a0b0c 100644 --- a/src/version.c +++ b/src/version.c @@ -696,6 +696,8 @@ static char *(features[]) = static int included_patches[] = { /* Add new patch number below this line */ /**/ + 1147, +/**/ 1146, /**/ 1145, diff --git a/src/vim9expr.c b/src/vim9expr.c index daf014f84..3acb97bef 100644 --- a/src/vim9expr.c +++ b/src/vim9expr.c @@ -263,6 +263,22 @@ compile_class_object_index(cctx_T *cctx, char_u **arg, type_T *type) return FAIL; } + if (type->tt_type == VAR_CLASS) + { + garray_T *instr = &cctx->ctx_instr; + if (instr->ga_len > 0) + { + isn_T *isn = ((isn_T *)instr->ga_data) + instr->ga_len - 1; + if (isn->isn_type == ISN_LOADSCRIPT) + { + // The class was recognized as a script item. We only need + // to know what class it is, drop the instruction. + --instr->ga_len; + vim_free(isn->isn_arg.script.scriptref); + } + } + } + ++*arg; char_u *name = *arg; char_u *name_end = find_name_end(name, NULL, NULL, FNE_CHECK_START); @@ -278,19 +294,6 @@ compile_class_object_index(cctx_T *cctx, char_u **arg, type_T *type) if (type->tt_type == VAR_CLASS) { - garray_T *instr = &cctx->ctx_instr; - if (instr->ga_len > 0) - { - isn_T *isn = ((isn_T *)instr->ga_data) + instr->ga_len - 1; - if (isn->isn_type == ISN_LOADSCRIPT) - { - // The class was recognized as a script item. We only need - // to know what class it is, drop the instruction. - --instr->ga_len; - vim_free(isn->isn_arg.script.scriptref); - } - } - function_count = cl->class_class_function_count; functions = cl->class_class_functions; } @@ -344,10 +347,8 @@ compile_class_object_index(cctx_T *cctx, char_u **arg, type_T *type) return FAIL; } - generate_GET_OBJ_MEMBER(cctx, i, m->ocm_type); - *arg = name_end; - return OK; + return generate_GET_OBJ_MEMBER(cctx, i, m->ocm_type); } } @@ -355,8 +356,20 @@ compile_class_object_index(cctx_T *cctx, char_u **arg, type_T *type) } else { - // TODO: class member - emsg("compile_class_object_index(): class member not handled yet"); + // load class member + int idx; + for (idx = 0; idx < cl->class_class_member_count; ++idx) + { + ocmember_T *m = &cl->class_class_members[idx]; + if (STRNCMP(name, m->ocm_name, len) == 0 && m->ocm_name[len] == NUL) + break; + } + if (idx < cl->class_class_member_count) + { + *arg = name_end; + return generate_CLASSMEMBER(cctx, TRUE, cl, idx); + } + semsg(_(e_class_member_not_found_str), name); } return FAIL; |