mirror of
https://github.com/vlang/v.git
synced 2023-08-10 21:13:21 +03:00
tools: new tool to extracts function names declared in V files
This commit is contained in:
parent
cd8b0d04bb
commit
eef73eea22
76
tools/vnames.v
Normal file
76
tools/vnames.v
Normal file
@ -0,0 +1,76 @@
|
|||||||
|
module main
|
||||||
|
|
||||||
|
import os
|
||||||
|
import flag
|
||||||
|
import compiler
|
||||||
|
|
||||||
|
const (
|
||||||
|
tool_version = '0.0.1'
|
||||||
|
tool_description = ' Extracts the function names declared in a v file.'
|
||||||
|
)
|
||||||
|
|
||||||
|
fn f_to_string(fmod string, f compiler.Fn) ?string {
|
||||||
|
svisibility := if f.is_public {
|
||||||
|
'public'
|
||||||
|
}else{
|
||||||
|
'private'
|
||||||
|
}
|
||||||
|
if fmod != f.v_fn_module() { return none }
|
||||||
|
if fmod == 'builtin' {
|
||||||
|
return '$svisibility\t' + f.v_fn_name()
|
||||||
|
}
|
||||||
|
return '$svisibility\t' + f.v_fn_module() + '.' + f.v_fn_name()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn analyze_v_file(file string) {
|
||||||
|
println('')
|
||||||
|
println('###################### $file ######################')
|
||||||
|
|
||||||
|
// main work:
|
||||||
|
mut v := compiler.new_v_compiler_with_args([file])
|
||||||
|
v.add_v_files_to_compile()
|
||||||
|
for f in v.files { v.parse(f, .decl) }
|
||||||
|
fi := v.get_file_parser_index( file ) or { panic(err) }
|
||||||
|
fmod := v.parsers[fi].mod
|
||||||
|
|
||||||
|
// output:
|
||||||
|
mut fns :=[]string
|
||||||
|
for _, f in v.table.fns {
|
||||||
|
fname := f_to_string(fmod, f) or { continue }
|
||||||
|
fns << fname
|
||||||
|
}
|
||||||
|
fns.sort()
|
||||||
|
for f in fns { println(f) }
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
fn main(){
|
||||||
|
toolexe := os.executable()
|
||||||
|
compiler.set_vroot_folder( os.dir(os.dir(toolexe)) )
|
||||||
|
|
||||||
|
mut fp := flag.new_flag_parser(os.args)
|
||||||
|
fp.application(os.filename(toolexe))
|
||||||
|
fp.version( tool_version )
|
||||||
|
fp.description( tool_description )
|
||||||
|
fp.arguments_description('FILE.v/FOLDER [FILE.v/FOLDER]...')
|
||||||
|
fp.limit_free_args_to_at_least(1)
|
||||||
|
fp.skip_executable()
|
||||||
|
show_help:=fp.bool_('help', `h`, false, 'Show this help screen\n')
|
||||||
|
if( show_help ){
|
||||||
|
println( fp.usage() )
|
||||||
|
exit(0)
|
||||||
|
}
|
||||||
|
|
||||||
|
mut files := []string
|
||||||
|
locations := fp.finalize() or { eprintln('Error: ' + err) exit(1) }
|
||||||
|
for xloc in locations {
|
||||||
|
loc := os.realpath(xloc)
|
||||||
|
xfiles := if os.is_dir(loc){ os.walk_ext(loc,'.v') } else { [loc] }
|
||||||
|
filtered_files := xfiles.filter(!it.ends_with('_js.v'))
|
||||||
|
files << filtered_files
|
||||||
|
}
|
||||||
|
|
||||||
|
for file in files {
|
||||||
|
analyze_v_file(file)
|
||||||
|
}
|
||||||
|
}
|
@ -141,7 +141,7 @@ pub fn (s array) left(n int) array {
|
|||||||
|
|
||||||
pub fn (s array) right(n int) array {
|
pub fn (s array) right(n int) array {
|
||||||
if n >= s.len {
|
if n >= s.len {
|
||||||
return s
|
return new_array(0, 0, s.element_size)
|
||||||
}
|
}
|
||||||
return s.slice(n, s.len)
|
return s.slice(n, s.len)
|
||||||
}
|
}
|
||||||
|
@ -121,6 +121,20 @@ fn test_right() {
|
|||||||
assert b[1] == 3
|
assert b[1] == 3
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn test_right_with_n_bigger_than_array_size() {
|
||||||
|
a := [1, 2, 3, 4]
|
||||||
|
mut b := a.right(10)
|
||||||
|
assert b.len == 0
|
||||||
|
|
||||||
|
// also check that the result of a.right
|
||||||
|
// is an array of the same type/element size as a:
|
||||||
|
b << 5
|
||||||
|
b << 6
|
||||||
|
assert b.len == 2
|
||||||
|
assert b[0] == 5
|
||||||
|
assert b[1] == 6
|
||||||
|
}
|
||||||
|
|
||||||
fn test_left() {
|
fn test_left() {
|
||||||
a := [1, 2, 3]
|
a := [1, 2, 3]
|
||||||
b := a.left(2)
|
b := a.left(2)
|
||||||
|
@ -11,7 +11,7 @@ import (
|
|||||||
|
|
||||||
fn (v mut V) cc() {
|
fn (v mut V) cc() {
|
||||||
v.build_thirdparty_obj_files()
|
v.build_thirdparty_obj_files()
|
||||||
vexe := os.executable()
|
vexe := vexe_path()
|
||||||
// Just create a C/JavaScript file and exit
|
// Just create a C/JavaScript file and exit
|
||||||
// for example: `v -o v.c compiler`
|
// for example: `v -o v.c compiler`
|
||||||
if v.out_name.ends_with('.c') || v.out_name.ends_with('.js') {
|
if v.out_name.ends_with('.c') || v.out_name.ends_with('.js') {
|
||||||
|
@ -12,8 +12,10 @@ const (
|
|||||||
MaxLocalVars = 50
|
MaxLocalVars = 50
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
struct Fn {
|
struct Fn {
|
||||||
// addr int
|
// addr int
|
||||||
|
pub:
|
||||||
mut:
|
mut:
|
||||||
name string
|
name string
|
||||||
mod string
|
mod string
|
||||||
@ -49,6 +51,11 @@ mut:
|
|||||||
done bool
|
done bool
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const (
|
||||||
|
EmptyFn = Fn{}
|
||||||
|
MainFn = Fn{ name: 'main' }
|
||||||
|
)
|
||||||
|
|
||||||
fn (a []TypeInst) str() string {
|
fn (a []TypeInst) str() string {
|
||||||
mut r := []string
|
mut r := []string
|
||||||
for t in a {
|
for t in a {
|
||||||
|
@ -211,11 +211,15 @@ pub fn (v mut V) compile() {
|
|||||||
cgen.genln('#define _VJS (1) ')
|
cgen.genln('#define _VJS (1) ')
|
||||||
}
|
}
|
||||||
|
|
||||||
if v.pref.building_v {
|
v_hash := vhash()
|
||||||
|
$if js {
|
||||||
|
cgen.genln('const V_COMMIT_HASH = "$v_hash";\n')
|
||||||
|
} $else {
|
||||||
cgen.genln('#ifndef V_COMMIT_HASH')
|
cgen.genln('#ifndef V_COMMIT_HASH')
|
||||||
cgen.genln('#define V_COMMIT_HASH "' + vhash() + '"')
|
cgen.genln('#define V_COMMIT_HASH "$v_hash"')
|
||||||
cgen.genln('#endif')
|
cgen.genln('#endif')
|
||||||
}
|
}
|
||||||
|
|
||||||
q := cgen.nogen // TODO hack
|
q := cgen.nogen // TODO hack
|
||||||
cgen.nogen = false
|
cgen.nogen = false
|
||||||
$if js {
|
$if js {
|
||||||
@ -471,13 +475,24 @@ pub fn final_target_out_name(out_name string) string {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn (v V) run_compiled_executable_and_exit() {
|
pub fn (v V) run_compiled_executable_and_exit() {
|
||||||
|
args := env_vflags_and_os_args()
|
||||||
|
|
||||||
if v.pref.is_verbose {
|
if v.pref.is_verbose {
|
||||||
println('============ running $v.out_name ============')
|
println('============ running $v.out_name ============')
|
||||||
}
|
}
|
||||||
mut cmd := '"' + final_target_out_name(v.out_name).replace('.exe','') + '"'
|
mut cmd := '"' + final_target_out_name(v.out_name).replace('.exe','') + '"'
|
||||||
if os.args.len > 3 {
|
|
||||||
cmd += ' ' + os.args.right(3).join(' ')
|
mut args_after := ' '
|
||||||
|
for i,a in args {
|
||||||
|
if i == 0 { continue }
|
||||||
|
if a.starts_with('-') { continue }
|
||||||
|
if a in ['run','test'] {
|
||||||
|
args_after += args.right(i+2).join(' ')
|
||||||
|
break
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
cmd += args_after
|
||||||
|
|
||||||
if v.pref.is_test {
|
if v.pref.is_test {
|
||||||
ret := os.system(cmd)
|
ret := os.system(cmd)
|
||||||
if ret != 0 {
|
if ret != 0 {
|
||||||
@ -855,7 +870,7 @@ pub fn new_v(args[]string) &V {
|
|||||||
_os = os_from_string(target_os)
|
_os = os_from_string(target_os)
|
||||||
}
|
}
|
||||||
// Location of all vlib files
|
// Location of all vlib files
|
||||||
vroot := os.dir(os.executable())
|
vroot := os.dir(vexe_path())
|
||||||
//println('VROOT=$vroot')
|
//println('VROOT=$vroot')
|
||||||
// v.exe's parent directory should contain vlib
|
// v.exe's parent directory should contain vlib
|
||||||
if !os.dir_exists(vroot) || !os.dir_exists(vroot + '/vlib/builtin') {
|
if !os.dir_exists(vroot) || !os.dir_exists(vroot + '/vlib/builtin') {
|
||||||
@ -933,23 +948,26 @@ pub fn new_v(args[]string) &V {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn env_vflags_and_os_args() []string {
|
pub fn env_vflags_and_os_args() []string {
|
||||||
mut args := []string
|
vosargs := os.getenv('VOSARGS')
|
||||||
vflags := os.getenv('VFLAGS')
|
if '' != vosargs { return vosargs.split(' ') }
|
||||||
if '' != vflags {
|
|
||||||
args << os.args[0]
|
mut args := []string
|
||||||
args << vflags.split(' ')
|
vflags := os.getenv('VFLAGS')
|
||||||
if os.args.len > 1 {
|
if '' != vflags {
|
||||||
args << os.args.right(1)
|
args << os.args[0]
|
||||||
}
|
args << vflags.split(' ')
|
||||||
} else{
|
if os.args.len > 1 {
|
||||||
args << os.args
|
args << os.args.right(1)
|
||||||
}
|
}
|
||||||
return args
|
} else{
|
||||||
|
args << os.args
|
||||||
|
}
|
||||||
|
return args
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn update_v() {
|
pub fn update_v() {
|
||||||
println('Updating V...')
|
println('Updating V...')
|
||||||
vroot := os.dir(os.executable())
|
vroot := os.dir(vexe_path())
|
||||||
s := os.exec('git -C "$vroot" pull --rebase origin master') or {
|
s := os.exec('git -C "$vroot" pull --rebase origin master') or {
|
||||||
verror(err)
|
verror(err)
|
||||||
return
|
return
|
||||||
@ -994,7 +1012,7 @@ pub fn install_v(args[]string) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
names := args.slice(2, args.len)
|
names := args.slice(2, args.len)
|
||||||
vexec := os.executable()
|
vexec := vexe_path()
|
||||||
vroot := os.dir(vexec)
|
vroot := os.dir(vexec)
|
||||||
vget := '$vroot/tools/vget'
|
vget := '$vroot/tools/vget'
|
||||||
if true {
|
if true {
|
||||||
@ -1020,7 +1038,7 @@ pub fn install_v(args[]string) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn create_symlink() {
|
pub fn create_symlink() {
|
||||||
vexe := os.executable()
|
vexe := vexe_path()
|
||||||
link_path := '/usr/local/bin/v'
|
link_path := '/usr/local/bin/v'
|
||||||
ret := os.system('ln -sf $vexe $link_path')
|
ret := os.system('ln -sf $vexe $link_path')
|
||||||
if ret == 0 {
|
if ret == 0 {
|
||||||
@ -1031,6 +1049,12 @@ pub fn create_symlink() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn vexe_path() string {
|
||||||
|
vexe := os.getenv('VEXE')
|
||||||
|
if '' != vexe { return vexe }
|
||||||
|
return os.executable()
|
||||||
|
}
|
||||||
|
|
||||||
pub fn verror(s string) {
|
pub fn verror(s string) {
|
||||||
println('V error: $s')
|
println('V error: $s')
|
||||||
os.flush_stdout()
|
os.flush_stdout()
|
||||||
@ -1067,3 +1091,21 @@ pub fn os_from_string(os string) OS {
|
|||||||
println('bad os $os') // todo panic?
|
println('bad os $os') // todo panic?
|
||||||
return .linux
|
return .linux
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
|
||||||
|
pub fn set_vroot_folder(vroot_path string) {
|
||||||
|
// Preparation for the compiler module:
|
||||||
|
// VEXE env variable is needed so that compiler.vexe_path()
|
||||||
|
// can return it later to whoever needs it:
|
||||||
|
mut vname := if os.user_os() == 'windows' { 'v.exe' } else { 'v' }
|
||||||
|
os.setenv('VEXE', os.realpath( [vroot_path, vname].join(os.path_separator) ), true)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn new_v_compiler_with_args(args []string) &V {
|
||||||
|
vexe := vexe_path()
|
||||||
|
mut allargs := [vexe]
|
||||||
|
allargs << args
|
||||||
|
os.setenv('VOSARGS', allargs.join(' '), true)
|
||||||
|
return new_v(allargs)
|
||||||
|
}
|
||||||
|
@ -40,7 +40,6 @@ mut:
|
|||||||
import_table FileImportTable // Holds imports for just the file being parsed
|
import_table FileImportTable // Holds imports for just the file being parsed
|
||||||
pass Pass
|
pass Pass
|
||||||
os OS
|
os OS
|
||||||
mod string
|
|
||||||
inside_const bool
|
inside_const bool
|
||||||
expr_var Var
|
expr_var Var
|
||||||
has_immutable_field bool
|
has_immutable_field bool
|
||||||
@ -80,13 +79,10 @@ mut:
|
|||||||
sql_params []string // ("select * from users where id = $1", ***"100"***)
|
sql_params []string // ("select * from users where id = $1", ***"100"***)
|
||||||
sql_types []string // int, string and so on; see sql_params
|
sql_types []string // int, string and so on; see sql_params
|
||||||
is_vh bool // parsing .vh file (for example `const (a int)` is allowed)
|
is_vh bool // parsing .vh file (for example `const (a int)` is allowed)
|
||||||
|
pub:
|
||||||
|
mod string
|
||||||
}
|
}
|
||||||
|
|
||||||
const (
|
|
||||||
EmptyFn = Fn{}
|
|
||||||
MainFn= Fn{name:'main'}
|
|
||||||
)
|
|
||||||
|
|
||||||
const (
|
const (
|
||||||
MaxModuleDepth = 4
|
MaxModuleDepth = 4
|
||||||
)
|
)
|
||||||
@ -1421,7 +1417,7 @@ fn ($v.name mut $v.typ) $p.cur_fn.name (...) {
|
|||||||
if p.assigned_type != p.expected_type {
|
if p.assigned_type != p.expected_type {
|
||||||
p.error_with_token_index( 'incompatible types: $p.assigned_type != $p.expected_type', errtok)
|
p.error_with_token_index( 'incompatible types: $p.assigned_type != $p.expected_type', errtok)
|
||||||
}
|
}
|
||||||
p.cgen.resetln('memcpy(& $left, $etype{$expr}, sizeof( $left ) );')
|
p.cgen.resetln('memcpy( (& $left), ($etype{$expr}), sizeof( $left ) );')
|
||||||
}
|
}
|
||||||
else if !p.builtin_mod && !p.check_types_no_throw(expr_type, p.assigned_type) {
|
else if !p.builtin_mod && !p.check_types_no_throw(expr_type, p.assigned_type) {
|
||||||
p.error_with_token_index( 'cannot use type `$expr_type` as type `$p.assigned_type` in assignment', errtok)
|
p.error_with_token_index( 'cannot use type `$expr_type` as type `$p.assigned_type` in assignment', errtok)
|
||||||
|
@ -8,7 +8,7 @@ import os
|
|||||||
import strings
|
import strings
|
||||||
|
|
||||||
struct Table {
|
struct Table {
|
||||||
mut:
|
pub mut:
|
||||||
typesmap map[string]Type
|
typesmap map[string]Type
|
||||||
consts []Var
|
consts []Var
|
||||||
fns map[string]Fn
|
fns map[string]Fn
|
||||||
@ -39,7 +39,7 @@ enum NameCategory {
|
|||||||
struct Name {
|
struct Name {
|
||||||
cat NameCategory
|
cat NameCategory
|
||||||
idx int // e.g. typ := types[name.idx]
|
idx int // e.g. typ := types[name.idx]
|
||||||
}
|
}
|
||||||
|
|
||||||
// Holds import information scoped to the parsed file
|
// Holds import information scoped to the parsed file
|
||||||
struct FileImportTable {
|
struct FileImportTable {
|
||||||
@ -74,6 +74,7 @@ enum TypeCategory {
|
|||||||
}
|
}
|
||||||
|
|
||||||
struct Var {
|
struct Var {
|
||||||
|
pub:
|
||||||
mut:
|
mut:
|
||||||
typ string
|
typ string
|
||||||
name string
|
name string
|
||||||
@ -102,6 +103,7 @@ mut:
|
|||||||
}
|
}
|
||||||
|
|
||||||
struct Type {
|
struct Type {
|
||||||
|
pub:
|
||||||
mut:
|
mut:
|
||||||
mod string
|
mod string
|
||||||
name string
|
name string
|
||||||
@ -198,7 +200,14 @@ fn (f Fn) str() string {
|
|||||||
return '$f.name($str_args) $f.typ'
|
return '$f.name($str_args) $f.typ'
|
||||||
}
|
}
|
||||||
|
|
||||||
fn (t &Table) debug_fns() string {
|
pub fn (f Fn) v_fn_module() string {
|
||||||
|
return f.mod
|
||||||
|
}
|
||||||
|
pub fn (f Fn) v_fn_name() string {
|
||||||
|
return f.name.replace('${f.mod}__', '')
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn (t &Table) debug_fns() string {
|
||||||
mut s := strings.new_builder(1000)
|
mut s := strings.new_builder(1000)
|
||||||
for _, f in t.fns {
|
for _, f in t.fns {
|
||||||
s.writeln(f.name)
|
s.writeln(f.name)
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
module main
|
module main
|
||||||
|
|
||||||
import vcompiler.tests.repl.runner
|
import compiler.tests.repl.runner
|
||||||
import log
|
import log
|
||||||
import benchmark
|
import benchmark
|
||||||
|
|
||||||
|
@ -17,7 +17,7 @@ mut:
|
|||||||
|
|
||||||
pub fn new_test_sesion(vargs string) TestSession {
|
pub fn new_test_sesion(vargs string) TestSession {
|
||||||
return TestSession{
|
return TestSession{
|
||||||
vexe: os.executable()
|
vexe: vexe_path()
|
||||||
vargs: vargs
|
vargs: vargs
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -118,7 +118,7 @@ pub fn (ts mut TestSession) test() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn v_test_v(args_before_test string){
|
pub fn v_test_v(args_before_test string){
|
||||||
vexe := os.executable()
|
vexe := vexe_path()
|
||||||
parent_dir := os.dir(vexe)
|
parent_dir := os.dir(vexe)
|
||||||
// Changing the current directory is needed for some of the compiler tests,
|
// Changing the current directory is needed for some of the compiler tests,
|
||||||
// compiler/tests/local_test.v and compiler/tests/repl/repl_test.v
|
// compiler/tests/local_test.v and compiler/tests/repl/repl_test.v
|
||||||
@ -163,7 +163,7 @@ pub fn v_test_v(args_before_test string){
|
|||||||
|
|
||||||
pub fn test_vget() {
|
pub fn test_vget() {
|
||||||
/*
|
/*
|
||||||
vexe := os.executable()
|
vexe := vexe_path()
|
||||||
ret := os.system('$vexe install nedpals.args')
|
ret := os.system('$vexe install nedpals.args')
|
||||||
if ret != 0 {
|
if ret != 0 {
|
||||||
println('failed to run v install')
|
println('failed to run v install')
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
|
|
||||||
module hash
|
module hash
|
||||||
|
|
||||||
interface Hash {
|
interface Hasher {
|
||||||
// Sum appends the current hash to b and returns the resulting array.
|
// Sum appends the current hash to b and returns the resulting array.
|
||||||
// It does not change the underlying hash state.
|
// It does not change the underlying hash state.
|
||||||
sum(b []byte) []byte
|
sum(b []byte) []byte
|
||||||
@ -12,10 +12,10 @@ interface Hash {
|
|||||||
block_size() int
|
block_size() int
|
||||||
}
|
}
|
||||||
|
|
||||||
interface Hash32 {
|
interface Hash32er {
|
||||||
sum32() u32
|
sum32() u32
|
||||||
}
|
}
|
||||||
|
|
||||||
interface Hash64 {
|
interface Hash64er {
|
||||||
sum64() u64
|
sum64() u64
|
||||||
}
|
}
|
||||||
|
@ -30,7 +30,7 @@ struct Asset {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// new_manager returns a new AssetManager
|
// new_manager returns a new AssetManager
|
||||||
pub fn new_manager() *AssetManager {
|
pub fn new_manager() &AssetManager {
|
||||||
return &AssetManager{}
|
return &AssetManager{}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user