# -*- coding: utf-8 -*-
"""
state_decoder
=============

Module for decoding the internal state of the HP3562A DSA, using the
GPIB command "DSBN" (Dump State BiNary).

This file can be exectued as a python script. Use '-h' for more informations. 
"""
from HP3562A import format_header, decode_float, decode_string, decode_header

from HP3562A.enum_types import *

HEADER = [("Measurement mode", EMEAS, 'h', 2),
          ("Measurement 1", EMTYP, 'h', 2),
          ("Measurement 2", EMTYP, 'h', 2),
          ("Window type", EWINTYP, 'h', 2),
          ("Force/Expon window 1", EFEXPW, 'h', 2),
          ("Force/Expon window 2", EFEXPW, 'h', 2),
          ("Average type", EAVGTYP, 'h', 2),
          ("Overlap percentage", int, 'h', 2),
          ("Number of averages", int, 'h', 2),
          ("Sweep # of averages", int, 'h', 2),
          ("Trigger type", ETRGTYP, 'h', 2),
          ("Trigger slope", ETRGSLP, 'h', 2),
          ("Preview type", EPRVTYP, 'h', 2),
          ("Sample type", ESMPTYP, 'h', 2),
          ("Range units chan 1", ERNGUNT, 'h', 2),
          ("Range units chan 2", ERNGUNT, 'h', 2),
          ("Range type 1", ERNGTYP, 'h', 2),
          ("Range type 2", ERNGTYP, 'h', 2),
          ("Input coupling 1", EINCPL, 'h', 2),
          ("Input coupling 2", EINCPL, 'h', 2),
          ("Source type", ESRCTYP, 'h', 2),
          ("Chirp percent", int, 'h', 2),
          ("Burst percent", int, 'h', 2),
          ("Sweep direction", ESWPDIR, 'h', 2),
          ("Sweep mode", ESWPMOD, 'h', 2),
          ("Ext sample freq untis", EXAXIS, 'h', 2),
          ("Bandwidth units", EXAXIS, 'h', 2),
          ("Log span index", int, 'h', 2),
          ("Log start index", int, 'h', 2),
          ("Sweep rate units", EXAXIS, 'h', 2),
          ("Auto gain ref chan", EDEMODCH, 'h', 2),
          ("Demod channels", EDEMODCH, 'h', 2),
          ("Demod type chan 1", EDEMOD, 'h', 2),
          ("Demod type chan 2", EDEMOD, 'h', 2),
          ("Source level units", EXAXIS, 'h', 2),
          ("Source offset units", EXAXIS, 'h', 2),
          ("Trigger level units", EXAXIS, 'h', 2),
          ("Capt/thru length units", EXAXIS, 'h', 2),
          ("EU label 1", str, 's', 6),
          ("EU label 2", str, 's', 6),
          ("Auto carrier on/off", bool, 'h', 2),
          ("Time average on/off", bool, 'h', 2),
          ("Auto/fixed resolution", bool, 'h', 2),
          ("Auto gain on/off", bool, 'h', 2),
          ("Auto/fixed integrate",bool, 'h', 2),
          ("Fast average on/off", bool, 'h', 2),
          ("Overload reject on/off", bool, 'h', 2),
          ("Chan 1 float/ground", bool, 'h', 2),
          ("Chan 2 float/ground", bool, 'h', 2),
          ("Time throughput on/off", bool, 'h', 2),
          ("Demodulation on/off", bool, 'h', 2),
          ("EU/volts chan 1", bool, 'h', 2),
          ("EU/volts chan 2", bool, 'h', 2),
          ("Manual/auto arm", bool, 'h', 2),
          ("Demod preview on/off", bool, 'h', 2),
          ("Delete freq on/off", bool, 'h', 2),
          ("Lin res Fstart pegged", bool, 'h', 2),
          ("Swept Fstart pegged", bool, 'h', 2),
          ("Force length chan 1", decode_float, None, 4),
          ("Force length chan 2", decode_float, None, 4),
          ("Expon time constant 1", decode_float, None, 4),
          ("Expon time constant 2", decode_float, None, 4),
          ("Sweep time", decode_float, None, 4),
          ("Sweep rate", decode_float, None, 4),
          ("Sweep resolution", decode_float, None, 4),
          ("Sweep integrate time", decode_float, None, 4),
          ("Auto gain level", decode_float, None, 4),
          ("Auto gain limit", decode_float, None, 4),
          ("Source level", decode_float, None, 4),
          ("EU value chan 1", decode_float, None, 4),
          ("EU value chan 2", decode_float, None, 4),
          ("Trigger delay chan 1", decode_float, None, 4),
          ("Trigger delay chan 2", decode_float, None, 4),
          ("Integrate var thresh", decode_float, None, 4),
          ("Capt/thru length", decode_float, None, 4),
          ("Frequency span", decode_float, None, 4),
          ("Time record length", decode_float, None, 4),
          ("Frequency resolution", decode_float, None, 4),
          ("Time resolution", decode_float, None, 4),
          ("External sample rate", decode_float, None, 4),
          ("Sample rate (actual)", decode_float, None, 4),
          ("Range channel 1", decode_float, None, 4),
          ("Range channel 2", decode_float, None, 4),
          ("Preview time", decode_float, None, 4),
          ("Trigger level", decode_float, None, 4),
          ("Source dc offset", decode_float, None, 4),
          ("Fixed sine frequency", decode_float, None, 8),
          ("Start frequency", decode_float, None, 8),
          ("Center frequency", decode_float, None, 8),
          ("Sweep start", decode_float, None, 8),
          ("Sweep end", decode_float, None, 8),
          ("Carrier frequency", decode_float, None, 8),
          ]
          
def decode_state(data):
    """
    Decode the data (as generated by the HP3562A DSA in response to a
    "DSBN" command), and returns a dict (header)

    header is the dictionnary of the header of the dumped data block,
    """
    header, idx = decode_header(data, HEADER)
    return header
    

def main():
    import sys
    import optparse
    opt = optparse.OptionParser("A simple tool for tracing a dumped trace")
    opt.add_option('-f', '--filename', default=None,
                   dest='filename',
                   help='Output filename. If not set, read from stdin')
    opt.add_option('-m', '--mode', default='binary',
                   dest='mode',
                   help='Dumping mode (may be "binary" [default], "ascii" or "ansi")',
                   )
    
    options, argv = opt.parse_args(sys.argv)


    if options.filename is None:
        print "Can't deal stdin for now..."
        sys.exit(1)
    #try:
    if 1:
        header = decode_state(open(options.filename, 'rb').read())
    else:
    #except Exception, e:
        print "ERROR: can't read %s an interpret it as a HP3562 trace"%options.filename
        print e
        sys.exit(1)

    print format_header(header, HEADER, 100)
    
if __name__ == "__main__":
    main()
          
