# encoding: utf-8 # frozen_string_literal: true module Carbon module Compiler module Visitor class Generation module Expressions module Calls Generation.on Node::Expression::Call::Access => :visit_expression_call_access def visit_expression_call_access(node, context) base = accept(node.expression, context) params = node.parameters.map { |p| accept(p, context) } ptypes = params.map(&:type) name = base.type.call(:[], [base.type, *ptypes], node.generics || []) func, gens = context.find(name) context.build.call(name, base, *params) .as(func.return.sub(gens)) end Generation.on Node::Expression::Call::Attribute => :visit_expression_call_attribute def visit_expression_call_attribute(node, context) base = accept(node.expression, context) name = base.type.call(node.name.value, [base.type], node.generics || []) func, gens = context.find(name) context.build.call(name, base).as(func.return.sub(gens)) end Generation.on Node::Expression::Call::Enum => :visit_expression_call_enum def visit_expression_call_enum(node, context) base = node.module params = node.parameters.map { |p| accept(p, context) } generics = node.generics.map { |p| accept(p, context) } ptypes = params.map(&:type) name = base.call(node.name.value, ptypes, node.generics || []) func, gens = context.find(name) context.build.call(name, *params).as(func.return.sub(gens)) end Generation.on Node::Expression::Call::Module => :visit_expression_call_module def visit_expression_call_module(node, context) base = node.module params = node.parameters.map { |p| accept(p, context) } ptypes = params.map(&:type) name = base.call(node.name.value, ptypes, node.generics || []) func, gens = context.find(name) context.build.call(name, *params).as(func.return.sub(gens)) end Generation.on Node::Expression::Call::Self => :visit_expression_call_self def visit_expression_call_self(node, context) base = @name params = node.parameters.map { |p| accept(p, context) } ptypes = params.map(&:type) name = base.call(node.name.value, [base, *ptypes], node.generics || []) func, gens = context.find(name) thisp = context.current.fetch("self") this = context.build.load(thisp).as(base) context.build.call(name, this, *params) .as(func.return.sub(gens)) end Generation.on Node::Expression::Call::Unified => :visit_expression_call_unified def visit_expression_call_unified(node, context) base = accept(node.expression, context) params = node.parameters.map { |p| accept(p, context) } generics = node.generics.map { |p| accept(p, context) } ptypes = params.map(&:type) name = base.type.call(node.name.value, [base.type, *ptypes], node.generics || []) func, gens = context.find(name) context.build.call(name, base, *params) .as(func.return.sub(gens)) end end end end end end end