# Copyright 2010, 2011 Free Software Foundation, Inc.

# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program.  If not, see <http://www.gnu.org/licenses/>.

if $tracelevel then {
	strace $tracelevel
}


if { ![istarget i?86-*-linux*] && ![istarget x86_64-*-linux* ] } {
    verbose "Skipping system register gcore tests."
    return
}

set testfile "system-gcore"
set srcfile  gcore.c
set binfile  ${objdir}/${subdir}/${testfile}

if  { [gdb_compile "${srcdir}/${subdir}/${srcfile}" "${binfile}" executable {debug}] != "" } {
     untested system-gcore.exp
     return -1
}

# Start with a fresh gdb.

gdb_exit
gdb_start
gdb_reinitialize_dir $srcdir/$subdir
gdb_load ${binfile}

# Does this gdb support gcore?
send_gdb "help gcore\n"
gdb_expect {
    -re "Undefined command: .gcore.*$gdb_prompt $" {
	# gcore command not supported -- nothing to test here.
	unsupported "gdb does not support gcore on this target"
	return -1;
    }
    -re "Save a core file .*$gdb_prompt $" {
	pass "help gcore"
    }
    -re ".*$gdb_prompt $" {
	fail "help gcore"
    }
    timeout {
	fail "help gcore (timeout)"
    }
}

if { ! [ runto_main ] } then {
    untested system-gcore.exp
    return -1
}

proc capture_command_output { command prefix } {
    global gdb_prompt
    global expect_out

    set output_string ""
    gdb_test_multiple "$command" "capture_command_output for $command" {
	-re "${command}\[\r\n\]+${prefix}(.*)\[\r\n\]+$gdb_prompt $" {
	    set output_string $expect_out(1,string)
	}
    }
    return $output_string
}

gdb_test "break terminal_func" "Breakpoint .* at .*${srcfile}, line .*" \
	"set breakpoint at terminal_func"

gdb_test "continue" "Breakpoint .* terminal_func.*" \
	"continue to terminal_func"

set print_prefix ".\[0123456789\]* = "

set pre_corefile_backtrace [capture_command_output "backtrace" ""]
set pre_corefile_regs [capture_command_output "info registers" ""]
set pre_corefile_allregs [capture_command_output "info all-reg" ""]
set pre_corefile_sysregs [capture_command_output "info reg system" ""]
set pre_corefile_static_array \
	[capture_command_output "print static_array" "$print_prefix"]
set pre_corefile_uninit_array \
	[capture_command_output "print un_initialized_array" "$print_prefix"]
set pre_corefile_heap_string \
	[capture_command_output "print heap_string" "$print_prefix"]
set pre_corefile_local_array \
	[capture_command_output "print array_func::local_array" "$print_prefix"]
set pre_corefile_extern_array \
	[capture_command_output "print extern_array" "$print_prefix"]

set escapedfilename [string_to_regexp ${objdir}/${subdir}/gcore.test]

set core_supported 0
gdb_test_multiple "gcore ${objdir}/${subdir}/gcore.test" \
	"save a corefile" \
{
  -re "Saved corefile ${escapedfilename}\[\r\n\]+$gdb_prompt $" {
    pass "save a corefile"
    global core_supported
    set core_supported 1
  }
  -re "Can't create a corefile\[\r\n\]+$gdb_prompt $" {
    unsupported "save a corefile"
    global core_supported
    set core_supported 0
  }
}

if {!$core_supported} {
  return -1
}

# Now restart gdb and load the corefile.
gdb_exit
gdb_start
gdb_reinitialize_dir $srcdir/$subdir
gdb_load ${binfile}

send_gdb "core ${objdir}/${subdir}/gcore.test\n"
gdb_expect {
    -re ".* is not a core dump:.*$gdb_prompt $" {
	fail "re-load generated corefile (bad file format)"
	# No use proceeding from here.
	return;	
    }
    -re ".*: No such file or directory.*$gdb_prompt $" {
	fail "re-load generated corefile (file not found)"
	# No use proceeding from here.
	return;	
    }
    -re ".*Couldn't find .* registers in core file.*$gdb_prompt $" {
	fail "re-load generated corefile (incomplete note section)"
    }
    -re "Core was generated by .*$gdb_prompt $" {
	pass "re-load generated corefile"
    }
    -re ".*$gdb_prompt $" {
	fail "re-load generated corefile"
    }
    timeout {
	fail "re-load generated corefile (timeout)"
    }
}

gdb_test_sequence "where" "where in corefile" {
    "\[\r\n\]+#0 .* terminal_func \\(\\) at "
    "\[\r\n\]+#1 .* array_func \\(\\) at "
    "\[\r\n\]+#2 .* factorial_func \\(value=1\\) at "
    "\[\r\n\]+#3 .* factorial_func \\(value=2\\) at "
    "\[\r\n\]+#4 .* factorial_func \\(value=3\\) at "
    "\[\r\n\]+#5 .* factorial_func \\(value=4\\) at "
    "\[\r\n\]+#6 .* factorial_func \\(value=5\\) at "
    "\[\r\n\]+#7 .* factorial_func \\(value=6\\) at "
    "\[\r\n\]+#8 .* main \\(.*\\) at "
}

set post_corefile_regs [capture_command_output "info registers" ""]
if ![string compare $pre_corefile_regs $post_corefile_regs] then {
    pass "corefile restored general registers"
} else {
    fail "corefile restored general registers"
}

set post_corefile_allregs [capture_command_output "info all-reg" ""]
if ![string compare $pre_corefile_allregs $post_corefile_allregs] then {
    pass "corefile restored all registers"
} else {
    fail "corefile restored all registers"
}

set post_corefile_sysregs [capture_command_output "info reg system" ""]
if ![string compare $pre_corefile_sysregs $post_corefile_sysregs] then {
    pass "corefile restored system registers"
} else {
    fail "corefile restored system registers"
}

set post_corefile_extern_array \
	[capture_command_output "print extern_array" "$print_prefix"]
if ![string compare $pre_corefile_extern_array $post_corefile_extern_array]  {
    pass "corefile restored extern array"
} else {
    fail "corefile restored extern array"
}

set post_corefile_static_array \
	[capture_command_output "print static_array" "$print_prefix"]
if ![string compare $pre_corefile_static_array $post_corefile_static_array]  {
    pass "corefile restored static array"
} else {
    fail "corefile restored static array"
}

set post_corefile_uninit_array \
	[capture_command_output "print un_initialized_array" "$print_prefix"]
if ![string compare $pre_corefile_uninit_array $post_corefile_uninit_array]  {
    pass "corefile restored un-initialized array"
} else {
    fail "corefile restored un-initialized array"
}

set post_corefile_heap_string \
	[capture_command_output "print heap_string" "$print_prefix"]
if ![string compare $pre_corefile_heap_string $post_corefile_heap_string]  {
    pass "corefile restored heap array"
} else {
    fail "corefile restored heap array"
}

set post_corefile_local_array \
	[capture_command_output "print array_func::local_array" "$print_prefix"]
if ![string compare $pre_corefile_local_array $post_corefile_local_array]  {
    pass "corefile restored stack array"
} else {
    fail "corefile restored stack array"
}

set post_corefile_backtrace [capture_command_output "backtrace" ""]
if ![string compare $pre_corefile_backtrace $post_corefile_backtrace]  {
    pass "corefile restored backtrace"
} else {
    fail "corefile restored backtrace"
}
