# Copyright 2002, 2003, 2004, 2005, 2007, 2008 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/>.

# Please email any bugs, comments, and/or additions to this file to:
# bug-gdb@prep.ai.mit.edu

# This file tests MI thread commands.
# Specifically, we are testing the MI command set and the console (in MI)
# command set ("interpreter-exec") and that the commands that are executed
# via these command pathways are properly executed. Console commands
# executed via MI should use MI output wrappers, MI event handlers, etc.

# This only works with native configurations
if {![isnative]} {
  return
}

load_lib mi-support.exp
set MIFLAGS "-i=mi2"

gdb_exit
if {[mi_gdb_start]} {
    continue
}

# The procs below dealing with parsing cli/mi output for the threadlist
# is duplicated in gdb669.exp. Any changes here will probably need to
# be made there as well.

proc get_mi_thread_list {name} {
  global expect_out

  # MI will return a list of thread ids:
  #
  # -thread-list-ids
  # ^done,thread-ids=[thread-id="1",thread-id="2",...],number-of-threads="N"
  # (gdb)
  mi_gdb_test "-thread-list-ids" \
    {\^done,thread-ids={(thread-id="[0-9]+"(,)?)+},number-of-threads="[0-9]+"} \
    "-thread_list_ids ($name)"

  set output {}
  if {[info exists expect_out(buffer)]} {
    set output $expect_out(buffer)
  }

  set thread_list {}
  if {![regexp {thread-ids=\{(thread-id="[0-9]+"(,)?)*\}} $output threads]} {
    fail "finding threads in MI output ($name)"
  } else {
    pass "finding threads in MI output ($name)"

    # Make list of console threads
    set start [expr {[string first \{ $threads] + 1}]
    set end   [expr {[string first \} $threads] - 1}]
    set threads [string range $threads $start $end]
    foreach thread [split $threads ,] {
      if {[scan $thread {thread-id="%d"} num]} {
	lappend thread_list $num
      }
    }
  }

  return $thread_list
}

# Check that MI and the console know of the same threads.
# Appends NAME to all test names.
proc check_mi_and_console_threads {name} {
  global expect_out

  mi_gdb_test "-thread-list-ids" \
    {\^done,thread-ids={(thread-id="[0-9]+"(,)*)+},number-of-threads="[0-9]+"} \
    "-thread-list-ids ($name)"
  set mi_output {}
  if {[info exists expect_out(buffer)]} {
    set mi_output $expect_out(buffer)
  }

  # GDB will return a list of thread ids and some more info:
  #
  # (gdb) 
  # -interpreter-exec console "info threads"
  # ~"  4 Thread 2051 (LWP 7734)  0x401166b1 in __libc_nanosleep () at __libc_nanosleep:-1"
  # ~"  3 Thread 1026 (LWP 7733)   () at __libc_nanosleep:-1"
  # ~"  2 Thread 2049 (LWP 7732)  0x401411f8 in __poll (fds=0x804bb24, nfds=1, timeout=2000) at ../sysdeps/unix/sysv/linux/poll.c:63"
  # ~"* 1 Thread 1024 (LWP 7731)  main (argc=1, argv=0xbfffdd94) at ../../../src/gdb/testsuite/gdb.mi/pthreads.c:160"
  # FIXME: kseitz/2002-09-05: Don't use the hack-cli method.
  mi_gdb_test "info threads" \
    {.*(~".*"[\r\n]*)+.*} \
    "info threads ($name)"
  set console_output {}
  if {[info exists $expect_out(buffer)]} {
    set console_output $expect_out(buffer)
  }

  # Make a list of all known threads to console (gdb's thread IDs)
  set console_thread_list {}
  foreach line [split $console_output \n] {
    if {[string index $line 0] == "~"} {
      # This is a line from the console; trim off "~", " ", "*", and "\""
      set line [string trim $line ~\ \"\*]
      if {[scan $line "%d" id] == 1} {
	lappend console_thread_list $id
      }
    }
  }

  # Now find the result string from MI
  set mi_result ""
  foreach line [split $mi_output \n] {
    if {[string range $line 0 4] == "^done"} {
      set mi_result $line
    }
  }
  if {$mi_result == ""} {
    fail "finding MI result string ($name)"
  } else {
    pass "finding MI result string ($name)"
  }

  # Finally, extract the thread ids and compare them to the console
  set num_mi_threads_str ""
  if {![regexp {number-of-threads="[0-9]+"} $mi_result num_mi_threads_str]} {
    fail "finding number of threads in MI output ($name)"
  } else {
    pass "finding number of threads in MI output ($name)"

    # Extract the number of threads from the MI result
    if {![scan $num_mi_threads_str {number-of-threads="%d"} num_mi_threads]} {
      fail "got number of threads from MI ($name)"
    } else {
      pass "got number of threads from MI ($name)"

      # Check if MI and console have same number of threads
      if {$num_mi_threads != [llength $console_thread_list]} {
	fail "console and MI have same number of threads ($name)"
      } else {
	pass "console and MI have same number of threads ($name)"

	# Get MI thread list
	set mi_thread_list [get_mi_thread_list $name]

	# Check if MI and console have the same threads
	set fails 0
	foreach ct [lsort $console_thread_list] mt [lsort $mi_thread_list] {
	  if {$ct != $mt} {
	    incr fails
	  }
	}
	if {$fails > 0} {
	  fail "MI and console have same threads ($name)"

	  # Send a list of failures to the log
	  send_log "Console has thread ids: $console_thread_list\n"
	  send_log "MI has thread ids: $mi_thread_list\n"
	} else {
	  pass "MI and console have same threads ($name)"
	}
      }
    }
  }
}

# This procedure tests the various thread commands in MI.
proc check_mi_thread_command_set {} {

  mi_runto done_making_threads

  set thread_list [get_mi_thread_list "in check_mi_thread_command_set"]
  
  mi_gdb_test "-thread-select" \
    {\^error,msg="mi_cmd_thread_select: USAGE: threadnum."} \
    "check_mi_thread_command_set: -thread-select"

  mi_gdb_test "-thread-select 123456789" \
    {&.*\^error,msg="Thread ID 123456789 not known\."} \
    "check_mi_thread_command_set: -thread-select 123456789"

  foreach thread $thread_list {
    # line and file are optional.
    # many of the threads are blocked in libc calls,
    # and many people have libc's with no symbols.
    mi_gdb_test "-thread-select $thread" \
      "\\^done,new-thread-id=\"$thread\",frame={.*}(,line=\"(-)?\[0-9\]+\",file=\".*\")?" \
      "check_mi_thread_command_set: -thread-select $thread"
  }
}

#
# Start here
#
set testfile "pthreads"
set srcfile "$testfile.c"
set binfile "$objdir/$subdir/mi2-$testfile"

set options [list debug incdir=$objdir]
if {[gdb_compile_pthreads "$srcdir/$subdir/$srcfile" $binfile executable $options] != "" } {
    return -1
}

mi_gdb_reinitialize_dir $srcdir/$subdir
mi_gdb_load $binfile

check_mi_thread_command_set

mi_gdb_exit

