# This test code is part of GDB, the GNU debugger.

# Copyright 1998-2000, 2003-2004, 2006-2012 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 "libgloss.exp"

# GCJ_UNDER_TEST is the compiler under test.

global tmpdir

if ![info exists tmpdir] {
    set tmpdir "/tmp"
}

set java_initialized 0

#
# Build the status wrapper library as needed.
#
proc java_init { args } {
    global wrapper_file;
    global wrap_compile_flags;
    global java_initialized
    global GCJ_UNDER_TEST
    global TOOL_EXECUTABLE
    global env

    if { $java_initialized == 1 } { return; }

    if ![info exists GCJ_UNDER_TEST] {
	if [info exists TOOL_EXECUTABLE] {
	    set GCJ_UNDER_TEST $TOOL_EXECUTABLE;
	} else {
	    if { [info exists env(GCJ)] && $env(GCJ) != "" } {
		set GCJ_UNDER_TEST $env(GCJ)
	    } else {
		global tool_root_dir
		global target_alias
		
		if ![is_remote host] {
		    set file [lookfor_file $tool_root_dir gcj];
		    if { $file == "" } {
			set file [lookfor_file $tool_root_dir gcc/gcj];
		    }
		    if { $file != "" } {
			set CC "$file -B[file dirname $file]/ --specs=$tool_root_dir/$target_alias/libjava/libgcj-test.spec";
		    } else {
			set CC [transform gcj];
		    }
		} else {
		    set CC [transform gcj]
		}
		set GCJ_UNDER_TEST $CC
	    }
	}
    }

    set wrapper_file "";
    set wrap_compile_flags "";
    if [target_info exists needs_status_wrapper] {
	set result [build_wrapper "testglue.o"];
	if { $result != "" } {
	    set wrapper_file [lindex $result 0];
	    set wrap_compile_flags [lindex $result 1];
	} else {
	    warning "Status wrapper failed to build."
	}
    }

    set java_initialized 1
}

#
# Run the test specified by srcfile and resultfile. compile_args and
# exec_args are options telling this proc how to work.
#
proc compile_java_from_source { srcfile binfile compile_args } {
    global GCJ_UNDER_TEST
    global java_initialized

    if { $java_initialized != 1 } { java_init }

    set args "compiler=$GCJ_UNDER_TEST"
    lappend args "additional_flags=--main=[file rootname [file tail $srcfile]]"
    if { $compile_args != "" } {
	lappend args "additional_flags=$compile_args"
    }

    set result [target_compile $srcfile ${binfile} executable $args]
    gdb_compile_test $srcfile $result
    return $result
}

# Auxiliary function to set the language to java.
# The result is 1 (true) for success, 0 (false) for failure.

proc set_lang_java {} {
    if [gdb_test_no_output "set language java"] {
	return 0
    }
    if [gdb_test "show language" ".* source language is \"java\"." \
	   "set language to \"java\""] {
	return 0
    }
    return 1;
}

# Local Variables:
# tcl-indent-level:4
# End:
