1
0
mirror of https://github.com/vlang/v.git synced 2023-08-10 21:13:21 +03:00

Compare commits

...

2 Commits

Author SHA1 Message Date
Hunam
c78d98c0ba @go -> golang 2022-07-01 16:07:43 +02:00
Hunam
1cb752f722 preliminary support for builtin functions, various fixes, various tweaks 2022-07-01 14:52:43 +02:00
12 changed files with 61 additions and 25 deletions

View File

@@ -0,0 +1,7 @@
module main
import v.builder.gobuilder
fn main() {
gobuilder.start()
}

View File

@@ -1,7 +0,0 @@
module main
import v.builder.golangbuilder
fn main() {
golangbuilder.start()
}

View File

@@ -178,7 +178,7 @@ fn rebuild(prefs &pref.Preferences) {
}
.golang {
println('using Go WIP backend...')
util.launch_tool(prefs.is_verbose, 'builders/golang_builder', os.args[1..])
util.launch_tool(prefs.is_verbose, 'builders/go_builder', os.args[1..])
}
}
}

View File

@@ -0,0 +1,5 @@
module builtin
pub fn println(s string) {
#fmt.Println(s.str)
}

View File

@@ -523,7 +523,7 @@ pub:
method_idx int
rec_mut bool // is receiver mutable
rec_share ShareType
language Language // V, C, JS
language Language // V, C, JS, Go
file_mode Language // whether *the file*, where a function was a '.c.v', '.js.v' etc.
no_body bool // just a definition `fn C.malloc()`
is_builtin bool // this function is defined in builtin/strconv

View File

@@ -35,6 +35,7 @@ pub enum Language {
v
c
js
golang
amd64 // aka x86_64
i386
arm64 // 64-bit arm

View File

@@ -523,7 +523,8 @@ pub fn (mut v Builder) cc() {
// whether to just create a .c or .js file and exit, for example: `v -o v.c cmd.v`
ends_with_c := v.pref.out_name.ends_with('.c')
ends_with_js := v.pref.out_name.ends_with('.js')
if ends_with_c || ends_with_js {
ends_with_go := v.pref.out_name.ends_with('.go')
if ends_with_c || ends_with_js || ends_with_go {
v.pref.skip_running = true
msg_mv := 'os.mv_by_cp $v.out_name_c => $v.pref.out_name'
util.timing_start(msg_mv)

View File

@@ -195,6 +195,9 @@ pub fn (v Builder) get_builtin_files() []string {
if v.pref.backend.is_js() {
builtin_files << v.v_files_from_dir(os.join_path(location, 'builtin',
'js'))
} else if v.pref.backend == .golang {
builtin_files << v.v_files_from_dir(os.join_path(location, 'builtin',
'go'))
} else {
builtin_files << v.v_files_from_dir(os.join_path(location, 'builtin'))
}

View File

@@ -1,4 +1,4 @@
module golangbuilder
module gobuilder
import os
import v.pref
@@ -9,17 +9,25 @@ import v.gen.golang
pub fn start() {
mut args_and_flags := util.join_env_vflags_and_os_args()[1..]
prefs, _ := pref.parse_args([], args_and_flags)
builder.compile('build', prefs, compile_golang)
builder.compile('build', prefs, compile_go)
}
pub fn compile_golang(mut b builder.Builder) {
// v.files << v.v_files_from_dir(os.join_path(v.pref.vlib_path,'builtin','bare'))
files := [b.pref.path]
pub fn compile_go(mut b builder.Builder) {
mut files := b.get_builtin_files()
files << b.get_user_files()
b.set_module_lookup_paths()
build_golang(mut b, files, b.pref.out_name)
if b.pref.is_verbose {
println('all .v files:')
println(files)
}
mut name := b.pref.out_name
if !name.ends_with('.go') {
name += '.go'
}
build_go(mut b, files, name)
}
pub fn build_golang(mut b builder.Builder, v_files []string, out_file string) {
pub fn build_go(mut b builder.Builder, v_files []string, out_file string) {
if b.pref.os == .windows {
if !b.pref.is_shared && b.pref.build_mode != .build_module
&& !b.pref.out_name.ends_with('.exe') {

View File

@@ -438,7 +438,7 @@ pub fn (mut c Checker) call_expr(mut node ast.CallExpr) ast.Type {
pub fn (mut c Checker) fn_call(mut node ast.CallExpr, mut continue_check &bool) ast.Type {
fn_name := node.name
if fn_name == 'main' {
if fn_name == 'main' && node.language != .golang {
c.error('the `main` function cannot be called in the program', node.pos)
}
mut has_generic := false // foo<T>() instead of foo<int>()
@@ -1292,8 +1292,9 @@ pub fn (mut c Checker) method_call(mut node ast.CallExpr) ast.Type {
} else {
c.fail_if_unreadable(node.left, left_type, 'receiver')
}
if left_sym.language != .js && (!left_sym.is_builtin() && method.mod != 'builtin')
&& method.language == .v && method.no_body {
if left_sym.language != .js && left_sym.language != .golang
&& (!left_sym.is_builtin() && method.mod != 'builtin') && method.language == .v
&& method.no_body {
c.error('cannot call a method that does not have a body', node.pos)
}
if node.concrete_types.len > 0 && method.generic_names.len > 0

View File

@@ -10,9 +10,10 @@ import v.pref
import os
const (
bs = '\\'
bs = '\\'
// when to break a line dependant on penalty
max_len = [0, 35, 60, 85, 93, 100]
max_len = [0, 35, 60, 85, 93, 100]
v_builtin_fns = ['println', 'print', 'eprintln', 'eprint', 'exit', 'panic']
)
pub struct Gen {
@@ -867,6 +868,7 @@ pub fn (mut f Gen) expr_stmt(node ast.ExprStmt) {
}
pub fn (mut f Gen) enum_decl(node ast.EnumDecl) {
// TODO(hunam6): transform to custom type + iota
f.attrs(node.attrs)
if node.is_pub {
f.write('pub ')
@@ -889,8 +891,15 @@ pub fn (mut f Gen) enum_decl(node ast.EnumDecl) {
}
pub fn (mut f Gen) fn_decl(node ast.FnDecl) {
f.attrs(node.attrs)
f.write(node.stringify(f.table, f.cur_mod, f.mod2alias).replace('fn ', 'func '))
v_fn_signature := node.stringify(f.table, f.cur_mod, f.mod2alias)
before_name_idx := v_fn_signature.index('fn') or { 0 } + 3 // will never equal 0
after_name_idx := v_fn_signature.index('(') or { 0 } // will never equal 0
mut name := v_fn_signature[before_name_idx..after_name_idx]
if v_fn_signature[..3] == 'pub' && name !in golang.v_builtin_fns {
name = name.capitalize()
}
f.write('func $name${v_fn_signature[after_name_idx..]}')
f.fn_body(node)
}
@@ -1124,6 +1133,7 @@ pub fn (mut f Gen) interface_method(method ast.FnDecl) {
}
pub fn (mut f Gen) module_stmt(mod ast.Module) {
dump(mod)
f.set_current_module_name(mod.name)
if mod.is_skipped {
return

View File

@@ -203,6 +203,9 @@ pub fn (mut p Parser) set_path(path string) {
'js' {
p.file_backend_mode = .js
}
'go' {
p.file_backend_mode = .golang
}
else {
arch := pref.arch_from_string(actual_language) or { pref.Arch._auto }
p.file_backend_mode = ast.pref_arch_to_table_language(arch)
@@ -3096,7 +3099,7 @@ fn (mut p Parser) module_decl() ast.Module {
mut module_pos := token.Pos{}
mut name_pos := token.Pos{}
mut mod_node := ast.Module{}
is_skipped := p.tok.kind != .key_module
mut is_skipped := p.tok.kind != .key_module
if is_skipped {
// the attributes were for something else != module, like a struct/fn/type etc.
module_attrs = []
@@ -3133,6 +3136,10 @@ fn (mut p Parser) module_decl() ast.Module {
full_name := util.qualify_module(p.pref, name, p.file_name)
p.mod = full_name
p.builtin_mod = p.mod == 'builtin'
// NOTE: Not so sure about that
if p.builtin_mod && p.file_backend_mode == .golang {
is_skipped = true
}
mod_node = ast.Module{
name: full_name
short_name: name