#!/usr/bin/env python
# -*- python -*-
#
# Copyright 2002 Free Software Foundation, Inc.
# 
# This file is part of GNU Radio
# 
# GNU Radio 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 2, or (at your option)
# any later version.
# 
# GNU Radio 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 GNU Radio; see the file COPYING.  If not, write to
# the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
# Boston, MA 02111-1307, USA.
# 

#
# Loopback the ATSC transmitter to the ATSC receiver and check that
# the output matches the input.  
#

# usage: test_full_loopback [options] [transport_stream]
#    -h, --help         help msg
#    -v, --verbose      verbose
#    -l, --log          enable RX logging
#    -L, --lms          enable LMS equalizer, else NOP equalizer
#    -g, --gui          enable RX GUI
#    -s 20, --20        i/o at 20 MS/s
#    -s 2x, --2x        i/o at 21.52 MS/s
#
# if no transport_stream if provided, fake.ts will be generated if needed, and used.


import os, os.path, math, sys, getopt


# set srcdir to the directory that contains Makefile.am

try:
    srcdir = os.environ['srcdir']
except KeyError, e:
    srcdir = "."
srcdir = srcdir + '/'


def system_chk (cmd):
    r = os.system (cmd)
    if (r != 0):
        # print "FAILED (%d): %s" % (r >> 8, cmd)
        if ((r & 0xff) != 0) :          # killed by signal
            sys.exit (127)
        else :
            sys.exit (r >> 8)
    return 0


def usage ():
    sys.stderr.write ("usage: %s [options] [mpeg_transport_stream]\n" % sys.argv[0])
    sys.stderr.write (
'''    -h, --help         this message
    -v, --verbose      verbose
    -l, --logging      enable RX logging
    -L, --lms          enable LMS equalizer, else NOP equalizer
    -g, --gui          enable RX GUI
    -s 20, --20        i/o at 20 MS/s
    -s 2x, --2x        i/o at 21.52 MS/s

    If mpeg_transport_stream is not provided, fake.ts will be generated if needed, and used.
''')
    sys.exit (1)

#
# parse command line args
#

s_option = ' -s 20'                   # default to 20 MS/s
atsc_rx_FLAGS = ''
atsc_tx_FLAGS = ''
verbose_p = 0
time_CMD = ''

try:
    opts, args = getopt.getopt(sys.argv[1:],
                               "hvlLgTs:",
                               ["help", "verbose", "logging", "lms", "gui", "time",
                                "20", "2x"])
except getopt.GetoptError:
    # print help information and exit:
    usage ()

input_ts = None
for o, a in opts:
    if o in ("-h", "--help"):
        usage ()
        sys.exit (0)
    if o in ("-v", "--verbose"):
        verbose_p = 1
    if o in ("-l", "--logging"):
        atsc_rx_FLAGS = atsc_rx_FLAGS + '-l '
    if o in ("-L", "--lms"):
        atsc_rx_FLAGS = atsc_rx_FLAGS + '-L '
    if o in ("-g", "--gui"):
        atsc_rx_FLAGS = atsc_rx_FLAGS + '-g '
    if o in ("-T", "--time"): 
        time_CMD = 'time '
    if o == '--20':
        s_option = ' -s 20'
    if o == '--2x':
        s_option = ' -s 2x'
    if o == '-s':
        if a == '20':
            s_option = ' -s 20'
        elif a == '2x':
            s_option = ' -s 2x'
        else:
            usage ()


if len (args) > 1:
    usage ()
if len (args) == 1:
    input_ts = args[0]
else:    
    input_ts = "fake.ts"
    if not os.path.exists (input_ts) :
        system_chk (srcdir + "make_fake_ts.py > " + input_ts)

atsc_rx_FLAGS = atsc_rx_FLAGS + s_option
atsc_tx_FLAGS = atsc_tx_FLAGS + s_option

#
# construct filenames for intermediate files
#

dst_dir = "."                           # destination directory for output and intermediates
input_base = os.path.basename (input_ts)

tx_samples    = os.path.join (dst_dir, input_base + ".txout")
output_ts     = os.path.join (dst_dir, input_base + ".rxout")

input_subset  = os.path.join (dst_dir, input_base + ".sub")
output_subset = os.path.join (dst_dir, input_base + ".rxout.sub")

files_to_cleanup = [ tx_samples, output_ts, input_subset, output_subset ]

#
# do the work
#

    
# run Tx and Rx
sys.stderr.write ("@@@\n@@@ Running Transmitter\n@@@\n")
system_chk (time_CMD + ("./atsc_tx %s -f %s -o %s"
                        % (atsc_tx_FLAGS, input_ts, tx_samples)))
sys.stderr.write ("@@@\n@@@ Running Receiver\n@@@\n")
system_chk (time_CMD + ("./atsc_rx %s -f %s -o %s"
                        % (atsc_rx_FLAGS, tx_samples, output_ts)))

#
# --- extract relevant parts of input and output files
#

osize = math.floor (os.path.getsize (output_ts) / 188)

interleaver_delay = 52
viterbi_delay = 12
pipeline_delay = interleaver_delay + viterbi_delay

dropped_fields = 1    # Always drop the first field because we don't see the 1st field sync.
                      #   We don't see the 1st field sync because our AGC, FPLL and
                      #   bit timing loop don't converge instantaneously

count = osize - pipeline_delay
system_chk ("dd if=%s of=%s bs=188 skip=%d count=%d" % (input_ts, input_subset,
                                                        dropped_fields * 312, count))
system_chk ("dd if=%s of=%s bs=188 skip=%d count=%d" % (output_ts, output_subset,
                                                        pipeline_delay, count))

#
# --- compare them
#

cmp_FLAGS = ''
if verbose_p:
    cmp_FLAGS = cmp_FLAGS + '-v '

# r = os.system ("cmp %s %s" % (input_subset, output_subset))
r = os.system (srcdir + ("cmp-mpeg.py %s %s %s" % (cmp_FLAGS,
                                                   input_subset, output_subset)))

# map (os.remove, files_to_cleanup)       # cleanup...

sys.exit (r >> 8)                       # return result code
