#########################################################################
""" wingdb.py    -- Top-level command used internally by Wing to
                    start a debug process.
                    
Copyright (c) 2000-2014, Archaeopteryx Software, Inc.  All rights reserved.

Written by Stephan R.A. Deibel and John P. Ehresman

"""
#########################################################################

# This is the non-patchable debugger startup module

import os.path
import sys

import _winghome

# Disable loading updates when running from sources or in a remote agent install
indicator_file = os.path.join(os.path.dirname(os.path.dirname(os.path.abspath(__file__))),
                              'src', 'debug', 'tserver', 'tracercore.c')
if os.path.exists(indicator_file):
  _winghome.kLoadUpdates = False
else:
  _winghome.kLoadUpdates = True

# For trouble-shooting, set environment variable or uncomment line below
def NP_GetDefaultPrintAllTracebacks():
  return os.environ.get('WINGDB_PRINT_ALL_TRACEBACKS', 0)
kPrintAllTracebacks = NP_GetDefaultPrintAllTracebacks()
if kPrintAllTracebacks:
  os.environ['WINGDB_PRINT_ALL_TRACEBACKS'] = '1'
  
# Set __file__ if not already set
try:
  __file__
except NameError:
  __file__ = sys.argv[0]

#----------------------------------------------------------------------
def NP_LoadModuleHere(modname):
  """Load the given module from same directory as this file
  without adding it to sys.modules"""

  sys.modules.pop(modname, None)

  sys.path.insert(0, os.path.dirname(__file__))
  exec('import %s' % modname)
  sys.modules.pop(modname, None)

  sys.path = sys.path[1:]
  return locals()[modname]
  
bootstrap_utils = NP_LoadModuleHere('bootstrap_utils')

#-----------------------------------------------------------------------
class NP_CTempLog:
  """ Temporarily log messages to a list until logging target is determined """

  def __init__(self):
    self.fEntries = []
    
  def out(self, *args):
    """ Save msg in fEntries """

    args = map(str, args)
    first = 1
    for s in args:
      if first:
        first = 0
      else:
        self.write(' ')
      self.write(s)
    
  def write(self, msg):
    """ Save msg in fEntries """
    
    if msg[-1:] == '\n':
      msg = msg[:-1]
    self.fEntries.append(msg)
    
  def write_entries(self, log):
    """ Write fEntries to out object via it's out method. """
    
    for entry in self.fEntries:
      log.out(entry)

  def clear(self):
    """ Clear all entries. """
    
    self.fEntries = []
  
#-----------------------------------------------------------------------
def NP_Initialize():
  """ Parse args and then run program. """

  logger = NP_CTempLog()

  # Find winghome and user settings directory and put into the _winghome module
  winghome = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))   
  winghome, user_settings = bootstrap_utils.NP_SetupWingHomeModule(winghome, print_errors=True)
    
  # Load the meta importer; everything after this block can be updated
  meta = bootstrap_utils.NP_CreateMetaImporter(winghome, user_settings,
                                               'dbg', logger=logger)

  # Log the meta importer directory list
  dir_list_repr = repr(meta.dir_list)
  if kPrintAllTracebacks:
    sys.__stderr__.write('Trying to import netserver from %s\n' % (dir_list_repr, ))
  if logger is not None:
    logger.write('Trying to import netserver from %s\n' % (dir_list_repr, ))
    
  return logger


#########################################################################
# Execution starts here
#########################################################################

if __name__ == '__main__':

  # Delete sys.path[0] because it refers to this file's directory
  del sys.path[0]

  # Save sys.modules and path/meta-path so we can restore them
  orig_sys_modules = list(sys.modules.keys())
  orig_sys_path = list(sys.path)
  orig_meta_path = list(sys.meta_path)
  
  # Initialize update manager; everything after this line can be updated
  logger = NP_Initialize()
  
  # Start debugging
  from debug.tserver import startdebug
  startdebug.kPrintAllTracebacks = kPrintAllTracebacks
  startdebug.StartDebug(logger, orig_sys_modules, orig_sys_path, orig_meta_path)

