compiler: -g and -debug should always add -g at least in the C compiler by default
* compiler: -g and -debug should always add -g at least in the C compiler by default. * Set first the C backend debug_options, so that the optimization_options can override them later. * Implement cleaner named is_debug, is_vlines, is_keep_c and is_cache options (i.e. -g/-cg, -keep_c, -cache v flags). * Check and reset file/line numbers in the generated main program, only if v.pref.is_vlines is true.pull/2312/head
parent
342e6a14a2
commit
065ce39577
|
@ -77,29 +77,30 @@ fn (v mut V) cc() {
|
||||||
println('Building ${v.out_name}...')
|
println('Building ${v.out_name}...')
|
||||||
}
|
}
|
||||||
|
|
||||||
mut debug_options := ''
|
debug_mode := v.pref.is_debug
|
||||||
|
mut debug_options := '-g'
|
||||||
mut optimization_options := '-O2'
|
mut optimization_options := '-O2'
|
||||||
if v.pref.ccompiler.contains('clang') {
|
if v.pref.ccompiler.contains('clang') {
|
||||||
if v.pref.is_debuggable {
|
if debug_mode {
|
||||||
debug_options = '-g -O0'
|
debug_options = '-g -O0'
|
||||||
}
|
}
|
||||||
optimization_options = '-O3 -flto'
|
optimization_options = '-O3 -flto'
|
||||||
}
|
}
|
||||||
if v.pref.ccompiler.contains('gcc') {
|
if v.pref.ccompiler.contains('gcc') {
|
||||||
if v.pref.is_debug {
|
if debug_mode {
|
||||||
debug_options = '-g3'
|
debug_options = '-g3'
|
||||||
}
|
}
|
||||||
optimization_options = '-O3 -fno-strict-aliasing -flto'
|
optimization_options = '-O3 -fno-strict-aliasing -flto'
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if debug_mode {
|
||||||
|
a << debug_options
|
||||||
|
}
|
||||||
if v.pref.is_prod {
|
if v.pref.is_prod {
|
||||||
a << optimization_options
|
a << optimization_options
|
||||||
}
|
}
|
||||||
else {
|
|
||||||
a << debug_options
|
if debug_mode && os.user_os() != 'windows'{
|
||||||
}
|
|
||||||
|
|
||||||
if v.pref.is_debuggable && os.user_os() != 'windows'{
|
|
||||||
a << ' -rdynamic ' // needed for nicer symbolic backtraces
|
a << ' -rdynamic ' // needed for nicer symbolic backtraces
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -115,7 +116,7 @@ fn (v mut V) cc() {
|
||||||
if v.pref.build_mode == .build_module {
|
if v.pref.build_mode == .build_module {
|
||||||
a << '-c'
|
a << '-c'
|
||||||
}
|
}
|
||||||
else if v.pref.is_debug {
|
else if v.pref.is_cache {
|
||||||
vexe := os.executable()
|
vexe := os.executable()
|
||||||
builtin_o_path := '$v_modules_path${os.PathSeparator}cache${os.PathSeparator}vlib${os.PathSeparator}builtin.o'
|
builtin_o_path := '$v_modules_path${os.PathSeparator}cache${os.PathSeparator}vlib${os.PathSeparator}builtin.o'
|
||||||
if os.file_exists(builtin_o_path) {
|
if os.file_exists(builtin_o_path) {
|
||||||
|
@ -225,7 +226,7 @@ fn (v mut V) cc() {
|
||||||
partial_output := res.output.limit(200).trim_right('\r\n')
|
partial_output := res.output.limit(200).trim_right('\r\n')
|
||||||
print(partial_output)
|
print(partial_output)
|
||||||
if res.output.len > partial_output.len {
|
if res.output.len > partial_output.len {
|
||||||
println('...\n(Use `v -debug` to print the entire error message)\n')
|
println('...\n(Use `v -g` to print the entire error message)\n')
|
||||||
}else{
|
}else{
|
||||||
println('')
|
println('')
|
||||||
}
|
}
|
||||||
|
@ -261,7 +262,7 @@ fn (v mut V) cc() {
|
||||||
println('linux cross compilation done. resulting binary: "$v.out_name"')
|
println('linux cross compilation done. resulting binary: "$v.out_name"')
|
||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
if !v.pref.is_debug && v.out_name_c != 'v.c' {
|
if !v.pref.is_keep_c && v.out_name_c != 'v.c' {
|
||||||
os.rm(v.out_name_c)
|
os.rm(v.out_name_c)
|
||||||
}
|
}
|
||||||
if v.pref.compress {
|
if v.pref.compress {
|
||||||
|
|
|
@ -807,7 +807,7 @@ fn (p mut Parser) fn_call_args(f mut Fn) &Fn {
|
||||||
p.check(.rpar)
|
p.check(.rpar)
|
||||||
return f
|
return f
|
||||||
}
|
}
|
||||||
// add debug information to panic when -debug arg is passed
|
// add debug information to panic when -g arg is passed
|
||||||
if p.v.pref.is_debug && f.name == 'panic' && !p.is_js {
|
if p.v.pref.is_debug && f.name == 'panic' && !p.is_js {
|
||||||
mod_name := p.mod.replace('_dot_', '.')
|
mod_name := p.mod.replace('_dot_', '.')
|
||||||
fn_name := p.cur_fn.name.replace('${p.mod}__', '')
|
fn_name := p.cur_fn.name.replace('${p.mod}__', '')
|
||||||
|
|
|
@ -82,13 +82,8 @@ fn (v &V) generate_hot_reload_code() {
|
||||||
msvc = '-os msvc'
|
msvc = '-os msvc'
|
||||||
}
|
}
|
||||||
|
|
||||||
mut debug := ''
|
so_debug_flag := if v.pref.is_debug { '-g' } else { '' }
|
||||||
|
cmd_compile_shared_library := '$vexe $msvc $so_debug_flag -o $file_base -shared $file'
|
||||||
if v.pref.is_debug {
|
|
||||||
debug = '-debug'
|
|
||||||
}
|
|
||||||
|
|
||||||
cmd_compile_shared_library := '$vexe $msvc $debug -o $file_base -shared $file'
|
|
||||||
if v.pref.show_c_cmd {
|
if v.pref.show_c_cmd {
|
||||||
println(cmd_compile_shared_library)
|
println(cmd_compile_shared_library)
|
||||||
}
|
}
|
||||||
|
|
|
@ -91,8 +91,14 @@ mut:
|
||||||
is_run bool
|
is_run bool
|
||||||
show_c_cmd bool // `v -show_c_cmd` prints the C command to build program.v.c
|
show_c_cmd bool // `v -show_c_cmd` prints the C command to build program.v.c
|
||||||
sanitize bool // use Clang's new "-fsanitize" option
|
sanitize bool // use Clang's new "-fsanitize" option
|
||||||
is_debuggable bool
|
|
||||||
is_debug bool // keep compiled C files
|
is_debug bool // false by default, turned on by -g or -cg, it tells v to pass -g to the C backend compiler.
|
||||||
|
is_vlines bool // turned on by -g, false by default (it slows down .tmp.c generation slightly).
|
||||||
|
is_keep_c bool // -keep_c , tell v to leave the generated .tmp.c alone (since by default v will delete them after c backend finishes)
|
||||||
|
// NB: passing -cg instead of -g will set is_vlines to false and is_g to true, thus making v generate cleaner C files,
|
||||||
|
// which are sometimes easier to debug / inspect manually than the .tmp.c files by plain -g (when/if v line number generation breaks).
|
||||||
|
is_cache bool // turns on v usage of the module cache to speed up compilation.
|
||||||
|
|
||||||
is_stats bool // `v -stats file_test.v` will produce more detailed statistics for the tests that were run
|
is_stats bool // `v -stats file_test.v` will produce more detailed statistics for the tests that were run
|
||||||
no_auto_free bool // `v -nofree` disable automatic `free()` insertion for better performance in some applications (e.g. compilers)
|
no_auto_free bool // `v -nofree` disable automatic `free()` insertion for better performance in some applications (e.g. compilers)
|
||||||
cflags string // Additional options which will be passed to the C compiler.
|
cflags string // Additional options which will be passed to the C compiler.
|
||||||
|
@ -460,14 +466,16 @@ fn (v mut V) generate_main() {
|
||||||
mut cgen := v.cgen
|
mut cgen := v.cgen
|
||||||
$if js { return }
|
$if js { return }
|
||||||
|
|
||||||
///// After this point, the v files are compiled.
|
if v.pref.is_vlines {
|
||||||
///// The rest is auto generated code, which will not have
|
///// After this point, the v files are compiled.
|
||||||
///// different .v source file/line numbers.
|
///// The rest is auto generated code, which will not have
|
||||||
lines_so_far := cgen.lines.join('\n').count('\n') + 5
|
///// different .v source file/line numbers.
|
||||||
cgen.genln('')
|
lines_so_far := cgen.lines.join('\n').count('\n') + 5
|
||||||
cgen.genln('////////////////// Reset the file/line numbers //////////')
|
cgen.genln('')
|
||||||
cgen.lines << '#line $lines_so_far "${cescaped_path(os.realpath(cgen.out_path))}"'
|
cgen.genln('////////////////// Reset the file/line numbers //////////')
|
||||||
cgen.genln('')
|
cgen.lines << '#line $lines_so_far "${cescaped_path(os.realpath(cgen.out_path))}"'
|
||||||
|
cgen.genln('')
|
||||||
|
}
|
||||||
|
|
||||||
// Make sure the main function exists
|
// Make sure the main function exists
|
||||||
// Obviously we don't need it in libraries
|
// Obviously we don't need it in libraries
|
||||||
|
@ -612,7 +620,7 @@ fn (v mut V) add_v_files_to_compile() {
|
||||||
mut builtin_files := v.get_builtin_files()
|
mut builtin_files := v.get_builtin_files()
|
||||||
// Builtin cache exists? Use it.
|
// Builtin cache exists? Use it.
|
||||||
builtin_vh := '$v_modules_path${os.PathSeparator}vlib${os.PathSeparator}builtin.vh'
|
builtin_vh := '$v_modules_path${os.PathSeparator}vlib${os.PathSeparator}builtin.vh'
|
||||||
if v.pref.is_debug && os.file_exists(builtin_vh) {
|
if v.pref.is_cache && os.file_exists(builtin_vh) {
|
||||||
v.cached_mods << 'builtin'
|
v.cached_mods << 'builtin'
|
||||||
builtin_files = [builtin_vh]
|
builtin_files = [builtin_vh]
|
||||||
}
|
}
|
||||||
|
@ -656,7 +664,7 @@ fn (v mut V) add_v_files_to_compile() {
|
||||||
if v.pref.build_mode != .build_module && !mod.contains('vweb') {
|
if v.pref.build_mode != .build_module && !mod.contains('vweb') {
|
||||||
mod_path := mod.replace('.', os.PathSeparator)
|
mod_path := mod.replace('.', os.PathSeparator)
|
||||||
vh_path := '$v_modules_path${os.PathSeparator}vlib${os.PathSeparator}${mod_path}.vh'
|
vh_path := '$v_modules_path${os.PathSeparator}vlib${os.PathSeparator}${mod_path}.vh'
|
||||||
if v.pref.is_debug && os.file_exists(vh_path) {
|
if v.pref.is_cache && os.file_exists(vh_path) {
|
||||||
println('using cached module `$mod`: $vh_path')
|
println('using cached module `$mod`: $vh_path')
|
||||||
v.cached_mods << mod
|
v.cached_mods << mod
|
||||||
v.files << vh_path
|
v.files << vh_path
|
||||||
|
@ -941,8 +949,12 @@ fn new_v(args[]string) &V {
|
||||||
is_so: '-shared' in args
|
is_so: '-shared' in args
|
||||||
is_prod: '-prod' in args
|
is_prod: '-prod' in args
|
||||||
is_verbose: '-verbose' in args || '--verbose' in args
|
is_verbose: '-verbose' in args || '--verbose' in args
|
||||||
is_debuggable: '-g' in args
|
|
||||||
is_debug: '-debug' in args || '-g' in args
|
is_debug: '-g' in args || '-cg' in args
|
||||||
|
is_vlines: '-g' in args && !('-cg' in args)
|
||||||
|
is_keep_c: '-keep_c' in args
|
||||||
|
is_cache: '-cache' in args
|
||||||
|
|
||||||
is_stats: '-stats' in args
|
is_stats: '-stats' in args
|
||||||
obfuscate: obfuscate
|
obfuscate: obfuscate
|
||||||
is_prof: '-prof' in args
|
is_prof: '-prof' in args
|
||||||
|
|
|
@ -213,7 +213,7 @@ fn find_msvc() ?MsvcResult {
|
||||||
pub fn (v mut V) cc_msvc() {
|
pub fn (v mut V) cc_msvc() {
|
||||||
r := find_msvc() or {
|
r := find_msvc() or {
|
||||||
// TODO: code reuse
|
// TODO: code reuse
|
||||||
if !v.pref.is_debug && v.out_name_c != 'v.c' && v.out_name_c != 'v_macos.c' {
|
if !v.pref.is_keep_c && v.out_name_c != 'v.c' && v.out_name_c != 'v_macos.c' {
|
||||||
os.rm(v.out_name_c)
|
os.rm(v.out_name_c)
|
||||||
}
|
}
|
||||||
verror('Cannot find MSVC on this OS')
|
verror('Cannot find MSVC on this OS')
|
||||||
|
@ -358,7 +358,7 @@ pub fn (v mut V) cc_msvc() {
|
||||||
// println(res)
|
// println(res)
|
||||||
// println('C OUTPUT:')
|
// println('C OUTPUT:')
|
||||||
|
|
||||||
if !v.pref.is_debug && v.out_name_c != 'v.c' && v.out_name_c != 'v_macos.c' {
|
if !v.pref.is_keep_c && v.out_name_c != 'v.c' && v.out_name_c != 'v_macos.c' {
|
||||||
os.rm(v.out_name_c)
|
os.rm(v.out_name_c)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -103,7 +103,7 @@ fn (v mut V) new_parser_from_string(text string, id string) Parser {
|
||||||
fn (v mut V) reset_cgen_file_line_parameters(){
|
fn (v mut V) reset_cgen_file_line_parameters(){
|
||||||
v.cgen.line = 0
|
v.cgen.line = 0
|
||||||
v.cgen.file = ''
|
v.cgen.file = ''
|
||||||
v.cgen.line_directives = v.pref.is_debuggable
|
v.cgen.line_directives = v.pref.is_vlines
|
||||||
}
|
}
|
||||||
|
|
||||||
fn (v mut V) new_parser_from_file(path string) Parser {
|
fn (v mut V) new_parser_from_file(path string) Parser {
|
||||||
|
|
|
@ -39,19 +39,28 @@ Options/commands:
|
||||||
-os <OS> Produce an executable for the selected OS.
|
-os <OS> Produce an executable for the selected OS.
|
||||||
OS can be linux, mac, windows, msvc.
|
OS can be linux, mac, windows, msvc.
|
||||||
Use msvc if you want to use the MSVC compiler on Windows.
|
Use msvc if you want to use the MSVC compiler on Windows.
|
||||||
|
-shared Build a shared library.
|
||||||
|
-stats Show additional stats when compiling/running tests. Try `v -stats test .`
|
||||||
|
|
||||||
|
-cache Turn on usage of the precompiled module cache.
|
||||||
|
It very significantly speeds up secondary compilations.
|
||||||
|
|
||||||
|
-obf Obfuscate the resulting binary.
|
||||||
|
- Shorthand for `v runrepl`.
|
||||||
|
|
||||||
|
Options for debugging/troubleshooting v programs:
|
||||||
|
-g Generate debugging information in the backtraces. Add *V* line numbers to the generated executable.
|
||||||
|
-cg Same as -g, but add *C* line numbers to the generated executable instead of *V* line numbers.
|
||||||
|
-keep_c Do NOT remove the generated .tmp.c files after compilation.
|
||||||
|
It is useful when using debuggers like gdb/visual studio, when given after -g / -cg .
|
||||||
|
-show_c_cmd Print the full C compilation command and how much time it took.
|
||||||
-cc <ccompiler> Specify which C compiler you want to use as a C backend.
|
-cc <ccompiler> Specify which C compiler you want to use as a C backend.
|
||||||
The C backend compiler should be able to handle C99 compatible C code.
|
The C backend compiler should be able to handle C99 compatible C code.
|
||||||
Common C compilers are gcc, clang, tcc, icc, cl...
|
Common C compilers are gcc, clang, tcc, icc, cl...
|
||||||
-cflags <flags> Pass additional C flags to the C backend compiler.
|
-cflags <flags> Pass additional C flags to the C backend compiler.
|
||||||
Example: -cflags `sdl2-config --cflags`
|
Example: -cflags `sdl2-config --cflags`
|
||||||
-debug Keep the generated C file for debugging in program.tmp.c even after compilation.
|
|
||||||
-shared Build a shared library.
|
|
||||||
-stats Show additional stats when compiling/running tests. Try `v -stats test .`
|
|
||||||
-g Show v line numbers in backtraces. Implies -debug.
|
|
||||||
-obf Obfuscate the resulting binary.
|
|
||||||
-show_c_cmd Print the full C compilation command and how much time it took.
|
|
||||||
- Shorthand for `v runrepl`.
|
|
||||||
|
|
||||||
|
Commands:
|
||||||
up Update V. Run `v up` at least once per day, since V development is rapid and features/bugfixes are added constantly.
|
up Update V. Run `v up` at least once per day, since V development is rapid and features/bugfixes are added constantly.
|
||||||
run <file.v> Build and execute the V program in file.v. You can add arguments for the V program *after* the file name.
|
run <file.v> Build and execute the V program in file.v. You can add arguments for the V program *after* the file name.
|
||||||
build <module> Compile a module into an object file.
|
build <module> Compile a module into an object file.
|
||||||
|
|
Loading…
Reference in New Issue