################################################################################
# Copyright (c) 2011 Trimble Navigation Ltd
# $Id: NoPi_parse_mtb.py,v 1.2 2011/03/25 01:14:44 acartmel Exp $
################################################################################
#
# NoPi_parse_mtb.py
#
# This is a simple script that can be used to parse the diffs_combo_X.mtb files
# generated by NoPi. It allows large .mtb to be reduced in size by only
# selecting certain ranges of time and/or by selecting data for a single
# satellite.
#
# It can also be used to split the .mtb file into a new file per SV.
#
# Reducing the file of the .mtb file will hopefully make some data analysis
# easier.
#
# See the show_help() function below for information on usage.
#
################################################################################

import sys;

################################################################################
# Function to display basic help and usage information if the command line
# options are not understood
################################################################################

def show_help() :
  print 'Expected command line is:'
  print '  python NoPi_parse_mtb.py [-s#] [-e#] [-p#] [-t] <diffs_combo_X.mtb file>'
  print 'Where:'
  print '  -s# defines the start time for data output'
  print '  -e# defines the end time for data output'
  print '      both default to all times otherwise'
  print '      NOTE: time in integer seconds only'
  print '  -p# defines a single SV Id for data output'
  print '      defaults to all SVs otherwise'
  print '  -t  split the .mtb file into files per SV'
  print '      generates files: diffs_combo_X_SV.mtb'
  print ' NOTE:'
  print '   The output is sent to the screen unless the -t option is selected'

################################################################################
# Simple function to convert a string into an integer value
# Used to decode the command line options
# Returns -1, option not selected, if the string is zero length
################################################################################

def get_value( strin ) :
  if ( len( strin ) == 0 ) :
    return( -1 )
  else :
    return( int( strin ) )

################################################################################
# Function to append a string to a file for a given SVId
# Creates a new file if this is a new SVId
################################################################################

def write_to_file( strin, sv ) :
  # Search for an already existing file for this SV
  found_file = 0
  for x in range( len( sv_list ) ) :
    if ( sv_list[x] == sv ) :
      # Found a file
      fout = file_list[x]
      found_file = 1
      break

  # Open a new file if this is the first data for this SV
  if ( found_file == 0 ) :
    # Construct the file name from the input file name
    # diffs_combo_0.mtb --> diffs_combo_0_sv.mtb
    fname = sys.argv[ len( sys.argv ) - 1 ]
    fname = fname.rsplit('.')
    fname = fname[0] + '_' + sv + '.' + fname[1]
    print 'Creating file ' + fname

    # Open the file and append to open file lists
    fout = open( fname, 'w' )
    file_list.append( fout )
    sv_list.append( sv )

  # Write the data to the file
  fout.write( strin )

################################################################################
# Close all the open files in the file list
################################################################################

def close_file_list() :
  for x in range( len( file_list ) ) :
    file_list[x].close()

################################################################################
# This is the start point for the script
################################################################################

# Initialise command line options to default values
start_time = -1 # No start time, process from start of file
end_time   = -1 # No end time, process to end of file
sel_sv     = -1 # No SV selected, process all satellites
split_file =  0 # Do not generate files for each satellite

# Initialise the file list when splitting the .mtb file
file_list = []
sv_list   = []

# Parse the command line arguments
# argv[0] is the script name
# argv[last] is the .mtb filename
unknown_arg = 0
for x in range( len( sys.argv ) - 2 ) :
  argv = sys.argv[x+1]

  # Test for valid switches
  if ( argv[0] == '-' ) :
    if ( argv[1] == 's' ) :
      start_time = get_value( argv[ 2 : len( argv ) ] )
    elif ( argv[1] == 'e' ) :
      end_time = get_value( argv[ 2 : len( argv ) ] )
    elif ( argv[1] == 'p' ) :
      sel_sv = get_value( argv[ 2 : len( argv ) ] )
    elif ( argv[1] == 't' ) :
      split_file = 1
    else :
      unknown_arg = 1
  else :
    unknown_arg = 1

# Test for valid command line arguments
if ( ( len( sys.argv ) < 2 ) | unknown_arg ) :
  show_help()
  sys.exit()

# Open the requested .mtb file
fin = open( sys.argv[ len( sys.argv ) - 1 ] )

# Read from the requested .mtb file until the end of the file
# is detected
line = fin.readline()
while( len( line ) ) :
  # Split the line into a list of strings
  slne = line.rsplit( ' ' )

  # Check for valid processing times and/or selected SVs
  if ( ( ( start_time == -1 ) | ( int( slne[0] )  >= start_time ) )
       & ( ( end_time == -1 ) | ( int( slne[0] ) <= end_time ) )
       & ( ( sel_sv == -1 ) | ( int( slne[1] ) == sel_sv ) )
     ) :
    # Determine the output mode
    if ( split_file ) :
      write_to_file( line, slne[1] )
    else :
      print line

  # Read next line
  line = fin.readline()

# Close all files in the file list, if used
if ( split_file ) :
  close_file_list()

# Close the requested .mtb file
fin.close()
