summaryrefslogtreecommitdiffhomepage
path: root/mrbgems/mruby-eval
AgeCommit message (Collapse)Author
2021-10-12Support Ruby3.0 keyword arguments.Yukihiro "Matz" Matsumoto
The Difference Since Ruby1.9, the keyword arguments were emulated by Ruby using the hash object at the bottom of the arguments. But we have gradually moved toward keyword arguments separated from normal (positinal) arguments. At the same time, we value compatibility, so that Ruby3.0 keyword arguments are somewhat compromise. Basically, keyword arguments are separated from positional arguments, except when the method does not take any formal keyword arguments, given keyword arguments (packed in the hash object) are considered as the last argument. And we also allow non symbol keys in the keyword arguments. In that case, those keys are just passed in the `**` hash (or raise `ArgumentError` for unknown keys). The Instruction Changes We have changed `OP_SEND` instruction. `OP_SEND` instruction used to take 3 operands, the register, the symbol, the number of (positional) arguments. The meaning of the third operand has been changed. It is now considered as `n|(nk<<4)`, where `n` is the number of positional arguments, and `nk` is the number of keyword arguments, both occupies 4 bits in the operand. The number `15` in both `n` and `nk` means variable sized arguments are packed in the object. Positional arguments will be packed in the array, and keyword arguments will be packed in the hash object. That means arguments more than 14 values are always packed in the object. Arguments information for other instructions (`OP_SENDB` and `OP_SUPER`) are also changed. It works as the third operand of `OP_SEND`. the difference between `OP_SEND` and `OP_SENDB` is just trivial. It assigns `nil` to the block hidden arguments (right after arguments). The instruction `OP_SENDV` and `OP_SENDVB` are removed. Those instructions are replaced by `OP_SEND` and `OP_SENDB` respectively with the `15` (variable sized) argument information. Calling Convention When calling a method, the stack elements shall be in the order of the receiver of the method, positional arguments, keyword arguments and the block argument. If the number of positional or keyword arugument (`n` or `nk`) is zero, corresponding arguments will be empty. So when `n=0` and `nk=0` the stack layout (from bottom to top) will be: +-----------------------+ | recv | block (or nil) | +-----------------------+ The last elements `block` should be explicitly filled before `OP_SEND` or assigned to `nil` by `OP_SENDB` internally. In other words, the following have exactly same behavior: OP_SENDB clears `block` implicitly: ``` OP_SENDB reg sym 0 ``` OP_SEND clears `block` implicitly: ``` OP_LOADNIL R2 OP_SEND R2 sym 0 ``` When calling a method with only positional arguments (n=0..14) without keyword arguments, the stack layout will be like following: +--------------------------------------------+ | recv | arg1 | ... | arg_n | block (or nil) | +--------------------------------------------+ When calling a method with arguments packed in the array (n=15) which means argument splat (*) is used in the actual arguments, or more than 14 arguments are passed the stack layout will be like following: +-------------------------------+ | recv | array | block (or nil) | +-------------------------------+ The number of the actual arguments is determined by the length of the argument array. When keyword arguments are given (nk>0), keyword arguments are passed between positional arguments and the block argument. For example, when we pass one positional argument `1` and one keyword argument `a: 2`, the stack layout will be like: +------------------------------------+ | recv | 1 | :a | 2 | block (or nil) | +------------------------------------+ Note that keyword arguments consume `2*nk` elements in the stack when `nk=0..14` (unpacked). When calling a method with keyword arguments packed in the hash object (nk=15) which means keyword argument splat (**) is used or more than 14 keyword arguments in the actual arguments, the stack layout will be like: +------------------------------+ | recv | hash | block (or nil) | +------------------------------+ Note for mruby/c When mruby/c authors try to support new keyword arguments, they need to handle the new meaning of the argument information operand. If they choose not to support keyword arguments in mruby/c, it just raise error when `nk` (taken by `(c>>4)&0xf`) is not zero. And combine `OP_SENDV` behavior with `OP_SEND` when `n` is `15`. If they want to support keyword arguments seriously, contact me at <[email protected]> or `@yukihiro_matz`. I can help you.
2021-09-07eval.c: if the parser raises an exception without an error messageYukihiro "Matz" Matsumoto
`eval` would have crashed in formatting.
2021-09-07eval.c: check length of the file name.Yukihiro "Matz" Matsumoto
It should be lexx than `UINT16_MAX`. If you don't check here, the parser would raise an exception.
2021-08-12test/eval.c: add test for #5528Yukihiro "Matz" Matsumoto
2021-07-19Remove unused prototypes for `mrb_proc_merge_lvar()`; ref #5511Yukihiro "Matz" Matsumoto
2021-06-28Merge pull request #5493 from dearblue/binding.2Yukihiro "Matz" Matsumoto
Fixed finding variables from `proc` in `binding.eval` failed
2021-06-26Fixed finding variables from `proc` in `binding.eval` faileddearblue
Previously the following code did not produce the expected results: ```ruby bx = binding block = bx.eval("a = 1; proc { a }") bx.eval("a = 2") p block.call # Expect 2 but return 1 due to a bug ``` The previous implementation of `Binding#eval` evaluated the code and then merged the top layer variables. This patch will parse and expand the variable space before making a call to `eval`. This means that the call to `Binding#eval` will do the parsing twice. In addition, the following changes will be made: - Make `mrb_parser_foreach_top_variable()`, `mrb_binding_extract_proc()` and `mrb_binding_extract_env()` functions private global functions. - Remove the `posthook` argument from `mrb_exec_irep()`. The `posthook` argument was introduced to implement the `binding` method. This patch is unnecessary because it uses a different implementation method. ref #5362 fixed #5491
2021-06-26Fix memory leak in `Kernel#eval`dearblue
The `mrbc_context` remained unreleased when the `mrb_parse_nstring()` function returned `NULL`.
2021-06-19Added `MRB_API` function to get block arguments info.dearblue
- ` mrb_block_given_p()` -- The name comes from CRuby's `rb_block_given_p ()` At the same time, it applies to `f_instance_eval()` and `f_class_eval()` of `mruby-eval`.
2021-06-16eval.c: implement `class_eval` with string; close #5478Yukihiro "Matz" Matsumoto
2021-04-03Make `mrb_exec_irep()` allow non-VM to enter.dearblue
Change the old `mrb_exec_irep()` as-is to static `mrb_exec_irep_vm()`. Extract the VM entry part from the old `exec_irep()` in `mruby-eval/src/eval.c` and make it the core of the new `mrb_exec_irep()`.
2021-02-26Use `MRB_SYM()` more extensively.Yukihiro "Matz" Matsumoto
2021-02-22Added other methods for `Binding`dearblue
- Added to `mruby-binding-core` - `Binding#local_variable_defined?` - `Binding#local_variable_get` - `Binding#local_variable_set` - `Binding#local_variables` - `Binding#receiver` - `Binding#source_location` - `Binding#inspect` - Added to `mruby-proc-binding` - `Proc#binding` The reason for separating `Proc#binding` is that core-mrbgems has a method that returns a closure object to minimize possible problems with being able to manipulate internal variables. By separating it as different mrbgem, each user can judge this problem and incorporate it arbitrarily.
2021-02-22Adjustment of the current HEAD and bindings, and separationdearblue
Make changes to make `Binding` work. At the same time, it separates `Binding#eval`, which depends on `mruby-eval`, from `mruby-binding-core`.
2021-02-22Merge branch 'binding' of https://github.com/ksss/mruby into HEADdearblue
2021-01-26Revert "Minimize the changes in #5277"Yukihiro "Matz" Matsumoto
This reverts commit dc51d89ac22acc60b9bfeed87115863565b74085.
2021-01-22Minimize the changes in #5277Yukihiro "Matz" Matsumoto
Instead of including `mruby/presym.h` everywhere, we provided the fallback `mruby/presym.inc` under `include/mruby` directory, and specify `-I<build-dir>/include` before `-I<top-dir>/include` in `presym.rake`. So even when someone drops `-I<build-dir>/include` in compiler options, it just compiles without failure.
2021-01-21Merge branch 'avoid-including-presym.inc-in-existing-header-files' of ↵Yukihiro "Matz" Matsumoto
https://github.com/shuujii/mruby into shuujii-avoid-including-presym.inc-in-existing-header-files
2021-01-11Avoid including `presym.inc` in existing header filesKOBAYASHI Shuji
Addressed an issue where existing programs linking `libmruby.a` could only be built by adding `<build-dir>/include` to compiler's include path.
2021-01-10Changes `stackent` to `stack` of `mrb_callinfo`dearblue
This enhances self-containment. Previously `mrb_context::stack` had the current call level stack, but now it owns it. The `mrb_context::stack` field, which is no longer needed, will be removed.
2021-01-10Unified `target_class` and `env` of `mrb_callinfo`dearblue
If there is `env`, `env->c` means `target_class`.
2020-12-25Improves out of memory messages for `eval`dearblue
The comment says that if `mrb_parse_nstring()` returns `NULL`, it is only out of memory. I'm worried about compatibility if I set the exception class to `NoMemoryError`, so it's still `RuntimeError`.
2020-10-24Reorganize `env_new()` as `mrb_env_new()`dearblue
The `mrb_env_new()` function is a global function, but it is still treated as an internal function.
2020-10-22Prohibit array changes by "a"/"*" specifier of `mrb_get_args()`dearblue
The "a"/"*" specifier of the `mrb_get_args()` function will now return `const mrb_value *`. This is because it is difficult for the caller to check if it is an array object and write-barrier if necessary. And it requires calling `mrb_ary_modify()` on the unmodified array object, which is also difficult (this is similar to #5087).
2020-10-12Fix warning from VC regarding implicit int conversion.Yukihiro "Matz" Matsumoto
2020-10-12Use functions that take symbols to reduce string litrals in C.Yukihiro "Matz" Matsumoto
2020-09-25Prohibit string changes by "s"/"z" specifier of `mrb_get_args()`dearblue
- The `s` specifier is a string pointer obtained without performing `mrb_str_modify()`, so it cannot be changed. - The `z` specifier cannot be changed because it is a string pointer obtained by `RSTRING_CSTR()` which returns `const char *`.
2020-06-25Change flag names in preparation of `REnv` refactoring.Yukihiro "Matz" Matsumoto
2020-06-02Remove `patch_irep()` in `mruby-eval`dearblue
- It can now deal with operands in the range of `OP_EXT*`. - It can now call the same method as the variable name without arguments. ```ruby def a "Safe!" end a = "Auto!" eval "a()" # call method `a` ```
2019-11-20Use proper `PEEK` macro for `OP_EPUSH` in `patch_irep`; fix #4833KOBAYASHI Shuji
2019-11-15Fix argument specs to `Kernel`KOBAYASHI Shuji
2019-08-18Prohibit changes to iseq in principledearblue
2019-08-05Use new specifiers/modifiers of `mrb_vfromat()`KOBAYASHI Shuji
The binary sizes (gems are only `mruby-bin-mruby`) are reduced slightly in my environment than before the introduction of new specifiers/modifiers (5116789a) with this change. ------------+-------------------+-------------------+-------- BINARY | BEFORE (5116789a) | AFTER (This PR) | RATIO ------------+-------------------+-------------------+-------- mruby | 593416 bytes | 593208 bytes | -0.04% libmruby.a | 769048 bytes | 767264 bytes | -0.23% ------------+-------------------+-------------------+-------- BTW, I accidentally changed `tasks/toolchains/visualcpp.rake` at #4613, so I put it back.
2019-07-15Unify type of line number to `uint16_t`KOBAYASHI Shuji
2019-05-18Move `Kernel#instance_eval` to `BasicObject`KOBAYASHI Shuji
2018-10-23Fixed a bug in processing `OP_EXT?` instructions.Yukihiro "Matz" Matsumoto
fix haconiwa/haconiwa#171
2018-10-02Fixed SEGV from `eval` called form top-level `mrb_funcall()`; fix #4028Yukihiro "Matz" Matsumoto
2018-09-01Move `Kernel#send` to `mruby-metaprog` gem.Yukihiro "Matz" Matsumoto
But `BasicObject#__send__` is still available from the core.
2018-08-30Separate meta-programming features to `mruby-metaprog` gem.Yukihiro "Matz" Matsumoto
We assume meta-programming is less used in embedded environments. We have moved following methods: * Kernel module global_variables, local_variables, singleton_class, instance_variables, instance_variables_defined?, instance_variable_get, instance_variable_set, methods, private_methods, public_methods, protected_methods, singleton_methods, define_singleton_methods * Module class class_variables, class_variables_defined?, class_variable_get, class_variable_set, remove_class_variable, included_modules, instance_methods, remove_method, method_removed, constants * Module class methods constants, nesting Note: Following meta-programming methods are kept in the core: * Module class alias_method, undef_method, ancestors, const_defined?, const_get, const_set, remove_const, method_defined?, define_method * Toplevel object define_method `mruby-metaprog` gem is linked by default (specified in default.gembox). When it is removed, it will save 40KB (stripped:8KB) on x86-64 environment last time I measured.
2018-08-25Reduce integer casting warnings.Yukihiro "Matz" Matsumoto
2018-08-25Should update `ci->env` to share the environment; fix #4073Yukihiro "Matz" Matsumoto
2018-07-30New bytecode implementation of mruby VM.Yukihiro "Matz" Matsumoto
2018-07-23Kernel#instance_eval should define singleton methods; fix #4069Yukihiro "Matz" Matsumoto
2018-06-06add test for evalIchito Nagata
2017-11-10Need to clear stack region for local variables in eval; fix #3844Yukihiro "Matz" Matsumoto
2017-10-28Fixed UPVAR gotchas; fix #3835Yukihiro "Matz" Matsumoto
Both `uvenv` function and `env` generation in `create_proc_from_string` function have bugs to handling enclosed environment objects.
2017-10-28Heavily refactored how lexical scope links are implemented; fix #3821Yukihiro "Matz" Matsumoto
Instead of `irep` links, we added a `upper` link to `struct RProc`. To make a space for the `upper` link, we moved `target_class` reference. If a `Proc` does not have `env`, `target_class` is saved in an `union` shared with `env` (if a `Proc` has env, you can tell it by `MRB_PROC_ENV_P()). Otherwise `target_class` is referenced from `env->c`. We removed links in `env` as well. This change removes 2 members from `mrb_irep` struct, thus saving 2 words per method/proc/block. This also fixes potential memory leaks due to the circular references caused by a link from `mrb_irep`.
2017-09-27fix: mrbgems\mruby-eval\src\eval.c(301): warning C4244: 'function': ↵Tomasz Dąbrowski
conversion from 'mrb_int' to 'int', possible loss of data
2017-09-27fix: mrbgems\mruby-eval\src\eval.c(214): warning C4244: '=': conversion from ↵Tomasz Dąbrowski
'mrb_int' to 'short', possible loss of data
2017-08-12Reduce integer type mismatch warnings in VC.Yukihiro "Matz" Matsumoto