mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
[Feature #16254] Allow __builtin.func
style
This commit is contained in:
parent
f3e081c6b6
commit
c8703a17ce
Notes:
git
2020-06-19 18:47:20 +09:00
2 changed files with 38 additions and 10 deletions
25
compile.c
25
compile.c
|
@ -7039,18 +7039,30 @@ iseq_builtin_function_lookup(const rb_iseq_t *iseq, const char *name)
|
||||||
}
|
}
|
||||||
|
|
||||||
static const char *
|
static const char *
|
||||||
iseq_builtin_function_name(ID mid)
|
iseq_builtin_function_name(const enum node_type type, const NODE *recv, ID mid)
|
||||||
{
|
{
|
||||||
const char *name = rb_id2name(mid);
|
const char *name = rb_id2name(mid);
|
||||||
static const char prefix[] = "__builtin_";
|
static const char prefix[] = "__builtin_";
|
||||||
const size_t prefix_len = sizeof(prefix) - 1;
|
const size_t prefix_len = sizeof(prefix) - 1;
|
||||||
|
|
||||||
if (UNLIKELY(strncmp(prefix, name, prefix_len) == 0)) {
|
if (type == NODE_CALL) {
|
||||||
return &name[prefix_len];
|
if (recv) {
|
||||||
|
switch (nd_type(recv)) {
|
||||||
|
case NODE_VCALL:
|
||||||
|
if (recv->nd_mid == rb_intern("__builtin")) {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
default: break;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else {
|
else if (type == NODE_VCALL || type == NODE_FCALL) {
|
||||||
return NULL;
|
if (UNLIKELY(strncmp(prefix, name, prefix_len) == 0)) {
|
||||||
|
return &name[prefix_len];
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
|
@ -7204,8 +7216,7 @@ compile_call(rb_iseq_t *iseq, LINK_ANCHOR *const ret, const NODE *const node, co
|
||||||
NODE *args_node = node->nd_args;
|
NODE *args_node = node->nd_args;
|
||||||
|
|
||||||
if (UNLIKELY(iseq_has_builtin_function_table(iseq)) &&
|
if (UNLIKELY(iseq_has_builtin_function_table(iseq)) &&
|
||||||
(type == NODE_VCALL || type == NODE_FCALL) &&
|
(builtin_func = iseq_builtin_function_name(type, node->nd_recv, mid)) != NULL) {
|
||||||
(builtin_func = iseq_builtin_function_name(mid)) != NULL) {
|
|
||||||
|
|
||||||
if (parent_block != NULL) {
|
if (parent_block != NULL) {
|
||||||
COMPILE_ERROR(iseq, line, "should not call builtins here.");
|
COMPILE_ERROR(iseq, line, "should not call builtins here.");
|
||||||
|
|
|
@ -72,7 +72,7 @@ end
|
||||||
|
|
||||||
def collect_builtin base, tree, name, bs, inlines, params = nil
|
def collect_builtin base, tree, name, bs, inlines, params = nil
|
||||||
while tree
|
while tree
|
||||||
call = sep = mid = args = nil
|
call = recv = sep = mid = args = nil
|
||||||
case tree.first
|
case tree.first
|
||||||
when :def
|
when :def
|
||||||
params = collect_params(tree[2])
|
params = collect_params(tree[2])
|
||||||
|
@ -93,6 +93,8 @@ def collect_builtin base, tree, name, bs, inlines, params = nil
|
||||||
when :method_add_arg
|
when :method_add_arg
|
||||||
_, mid, (_, (_, args)) = tree
|
_, mid, (_, (_, args)) = tree
|
||||||
case mid.first
|
case mid.first
|
||||||
|
when :call
|
||||||
|
_, recv, sep, mid = mid
|
||||||
when :fcall
|
when :fcall
|
||||||
_, mid = mid
|
_, mid = mid
|
||||||
else
|
else
|
||||||
|
@ -102,12 +104,27 @@ def collect_builtin base, tree, name, bs, inlines, params = nil
|
||||||
_, mid = tree
|
_, mid = tree
|
||||||
when :command # FCALL
|
when :command # FCALL
|
||||||
_, mid, (_, args) = tree
|
_, mid, (_, args) = tree
|
||||||
|
when :call, :command_call # CALL
|
||||||
|
_, recv, sep, mid, (_, args) = tree
|
||||||
end
|
end
|
||||||
if mid
|
if mid
|
||||||
raise "unknown sexp: #{mid.inspect}" unless mid.first == :@ident
|
raise "unknown sexp: #{mid.inspect}" unless mid.first == :@ident
|
||||||
_, mid, (lineno,) = mid
|
_, mid, (lineno,) = mid
|
||||||
if /\A__builtin_(.+)/ =~ mid
|
if recv
|
||||||
cfunc_name = func_name = $1
|
func_name = nil
|
||||||
|
case recv.first
|
||||||
|
when :vcall
|
||||||
|
_, recv = recv
|
||||||
|
if recv.first == :@ident and recv[1] == "__builtin"
|
||||||
|
func_name = mid.to_s
|
||||||
|
end
|
||||||
|
end
|
||||||
|
collect_builtin(base, recv, name, bs, inlines) unless func_name
|
||||||
|
else
|
||||||
|
func_name = mid[/\A__builtin_(.+)/, 1]
|
||||||
|
end
|
||||||
|
if func_name
|
||||||
|
cfunc_name = func_name
|
||||||
args.pop unless (args ||= []).last
|
args.pop unless (args ||= []).last
|
||||||
argc = args.size
|
argc = args.size
|
||||||
|
|
||||||
|
|
Loading…
Add table
Reference in a new issue