# Copyright 2013-2021 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/>.

load_lib dwarf.exp

# This test can only be run on targets which support DWARF-2.
if {![dwarf2_support]} {
    return 0
}

standard_testfile main.c

if { [prepare_for_testing "failed to prepare" "${testfile}" \
	  [list ${srcfile}]] } {
    return -1
}

# Add a .gdb_index section to PROGRAM.
# PROGRAM is assumed to be the output of standard_output_file.
# Returns the path of the program or "" if there is a failure.
# If there is a failure it will have already been logged.
# Use local prefix to prevent overriding add_gdb_index from lib/gdb.exp.

proc local_add_gdb_index { program } {
    set index_file ${program}.gdb-index
    set dir [file dirname ${program}]
    set filename [file tail ${program}]
    set dwz $dir/.tmp/${filename}.dwz
    set dwz_index_file $program.dwz.gdb-index
    verbose -log "index_file: ${index_file}"
    remote_file host delete ${index_file}
    remote_file host delete ${dwz_index_file}
    gdb_test_no_output "save gdb-index [file dirname ${index_file}]" \
	"save gdb-index for file [file tail ${program}]"

    # No point in continuing if generating the index failed.
    # N.B.: There are times when gdb won't create an index, and it's not a
    # failure.  However, in our case we need an index.  So if you find one
    # not being generated, you'll either have to tweak the .c file or maybe
    # add a flag to force an index to be generated.
    if { [remote_file host exists ${index_file}] } {
	pass "gdb-index file created"
    } else {
	fail "gdb-index file created"
	return ""
    }

    set program_with_index ${program}.with-index
    if {[run_on_host "objcopy" [gdb_find_objcopy] "--remove-section .gdb_index --add-section .gdb_index=$index_file --set-section-flags .gdb_index=readonly ${program} ${program_with_index}"]} {
	return ""
    }

    with_test_prefix "modify dwz file" {
	if { [remote_file host exists ${dwz_index_file}] } {
	    # We're modifying $dwz in place, otherwise we'd have to update
	    # .gnu_debugaltlink in $program.
	    set args [join [list "--remove-section .gdb_index" \
				" --add-section .gdb_index=$dwz_index_file" \
				" --set-section-flags .gdb_index=readonly $dwz"]]
	    if {[run_on_host "objcopy" [gdb_find_objcopy] "$args"]} {
		return ""
	    }
	}
    }

    return ${program_with_index}
}

# Build a copy of the program with an index (.gdb_index/.debug_names).
# But only if the toolchain didn't already create one: gdb doesn't support
# building an index from a program already using one.

set test "check if index present"
gdb_test_multiple "mt print objfiles ${testfile}" $test {
    -re "gdb_index.*${gdb_prompt} $" {
	set binfile_with_index $binfile
    }
    -re "debug_names.*${gdb_prompt} $" {
	set binfile_with_index $binfile
    }
    -re "Psymtabs.*${gdb_prompt} $" {
	set binfile_with_index [local_add_gdb_index $binfile]
	if { ${binfile_with_index} == "" } {
	    return -1
	}
    }
}

# Ok, we have a copy of $binfile with an index.
# Restart gdb and verify the index was used.

clean_restart ${binfile_with_index}
gdb_test "mt print objfiles ${testfile}" \
    "(gdb_index|debug_names).*" \
    "index used"

# Make gdb re-read symbols and see if .gdb_index/.debug_names still
# gets used.  symtab/15885

# There is gdb_touch_execfile, but it doesn't handle remote hosts.
# Is touch portable enough?
# First make sure enough time has passed, file mtime resolution is seconds.
gdb_test_no_output "shell sleep 1"
if {[run_on_host "touch binary" touch ${binfile_with_index}]} {
    return -1
}

if ![runto_main] {
    return -1
}
gdb_test "mt print objfiles ${testfile}" \
    "(gdb_index|debug_names).*" \
    "index used after symbol reloading"
