#!/usr/bin/python

import sys
import dbus
import json
import xml.etree.ElementTree as ET


def fix_byte(it, key, parent):
    if (isinstance(it, dbus.Array)):
        for i in range(0, len(it)):
            fix_byte(it[i], i, it)
    elif (isinstance(it, dict)):
        for key in it.keys():
            fix_byte(it[key], key, it)
    elif (isinstance(it, dbus.Byte)):
        if (key != None):
            parent[key] = int(it)
    elif (isinstance(it, dbus.Double)):
        if (key != None):
            parent[key] = float(it)
    else:
        pass


def merge_interfaces(objs):
    for op in objs:
        merged = {}
        for interface, properties in objs[op].items():
            merged.update(properties)

        del objs[op]
        objs[op] = merged


def printDict(name, data):
    if (isinstance(data, dict)):
        print ">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>"
        print name
        for p in sorted(data.keys()):
            printDict(p, data[p])
    else:
        print name + " = " + str(data)


def introspect(bus_name, obj_path, intf_name, method_name):
    obj = bus.get_object(bus_name, obj_path)
    introspect_iface = dbus.Interface(obj,
                                      "org.freedesktop.DBus.Introspectable")
    tree = ET.ElementTree(ET.fromstring(introspect_iface.Introspect()))
    # print method_name
    # print introspect_iface.Introspect()
    root = tree.getroot()
    found = False
    for node in root.iter('node'):
        for intf in node.iter('interface'):
            if (intf.attrib['name'] == intf_name):
                for method in intf.iter('method'):
                    if (method.attrib['name'] == method_name):
                        for ar in method.iter('arg'):
                            if (ar.attrib['direction'] == "in"):
                                print "\t" + ar.attrib['name'] + " (" + \
                                      ar.attrib['type'] + ")"
                                found = True

    return found


dbus_objects = {
    'power': {
        'bus_name': 'org.openbmc.control.Power',
        'object_name': '/org/openbmc/control/power0',
        'interface_name': 'org.openbmc.control.Power'
    },
    'identify_led': {
        'bus_name': 'org.openbmc.control.led',
        'object_name': '/org/openbmc/control/led/identify',
        'interface_name': 'org.openbmc.Led'
    },
    'chassis': {
        'bus_name': 'org.openbmc.control.Chassis',
        'object_name': '/org/openbmc/control/chassis0',
        'interface_name': 'org.openbmc.control.Chassis'
    },
    'poweron': {
        'bus_name': 'xyz.openbmc_project.State.Host',
        'object_name': '/xyz/openbmc_project/state/host0',
        'interface_name': 'xyz.openbmc_project.State.Host',
        'property': 'RequestedHostTransition',
        'value': 'xyz.openbmc_project.State.Host.Transition.On'
    },
    'poweroff': {
        'bus_name': 'xyz.openbmc_project.State.Host',
        'object_name': '/xyz/openbmc_project/state/host0',
        'interface_name': 'xyz.openbmc_project.State.Host',
        'property': 'RequestedHostTransition',
        'value': 'xyz.openbmc_project.State.Host.Transition.Off'
    },
    'state': {
        'bus_name': 'org.openbmc.managers.System',
        'object_name': '/org/openbmc/managers/System',
        'interface_name': 'org.openbmc.managers.System',
        'method': 'getSystemState',
    },
    'bootprogress': {
        'bus_name': 'org.openbmc.Sensors',
        'object_name': '/org/openbmc/sensors/host/BootProgress',
        'interface_name': 'org.openbmc.SensorValue'
    },
    'biosupdate': {
        'bus_name': 'org.openbmc.control.Flash',
        'object_name': '/org/openbmc/control/flash/bios',
        'interface_name': 'org.openbmc.Flash',
        'method': 'updateViaTftp',
    },
    'biosflash': {
        'bus_name': 'org.openbmc.control.Flash',
        'object_name': '/org/openbmc/control/flash/bios',
        'interface_name': 'org.openbmc.Flash',
    },
    'bmcupdate': {
        'bus_name': 'org.openbmc.control.BmcFlash',
        'object_name': '/org/openbmc/control/flash/bmc',
        'interface_name': 'org.openbmc.control.BmcFlash',
        'method': 'updateViaTftp',
    },
    'bmcflash': {
        'bus_name': 'org.openbmc.control.BmcFlash',
        'object_name': '/org/openbmc/control/flash/bmc',
        'interface_name': 'org.openbmc.control.BmcFlash',
    },
    'getinventory': {
        'bus_name': 'org.openbmc.Inventory',
        'object_name': '/org/openbmc/inventory',
        'interface_name': 'org.freedesktop.DBus.ObjectManager',
        'method': 'GetManagedObjects',
        'transform': merge_interfaces
    },
    'getsensors': {
        'bus_name': 'org.openbmc.Sensors',
        'object_name': '/org/openbmc/sensors',
        'interface_name': 'org.freedesktop.DBus.ObjectManager',
        'method': 'GetManagedObjects',
        'transform': merge_interfaces
    },
    'host': {
        'bus_name': 'org.openbmc.control.Host',
        'object_name': '/org/openbmc/control/host0',
        'interface_name': 'org.openbmc.control.Host',
    },
    'setdebugmode': {
        'bus_name': 'org.openbmc.control.Host',
        'object_name': '/org/openbmc/control/host0',
        'interface_name': 'org.openbmc.control.Host',
        'property': 'debug_mode'
    },
}

bus = dbus.SystemBus()

if (len(sys.argv) == 1 or sys.argv[1] == "-h" or dbus_objects.has_key(
        sys.argv[1]) == False):
    print "Usage: obmcutil [command] [[method] [*args]]"
    print "\tIf [method] is blank, then all properties are printed\n"
    print "Available commands:"
    for name in sorted(dbus_objects.keys()):
        m = ""
        if (dbus_objects[name].has_key('method') == True):
            m = " (" + dbus_objects[name]['interface_name'] + "->" + \
                dbus_objects[name]['method'] + ")"
        elif (dbus_objects[name].has_key('property') == True):
            m = " (" + dbus_objects[name]['interface_name'] + "->" + \
                dbus_objects[name]['property'] + ")"

        print "\t" + name + m
    exit(0)

method_name = ""
property_name = ""

sys.argv.pop(0)
objinfo = dbus_objects[sys.argv.pop(0)]

if (objinfo.has_key('method')):
    method_name = objinfo['method']
elif (objinfo.has_key('property')):
    property_name = objinfo['property']
elif (len(sys.argv) > 0):
    ## if command line args left and method not specified
    ## then next arg must be method name
    method_name = sys.argv.pop(0)

bus_name = objinfo['bus_name']
obj_path = objinfo['object_name']
intf_name = objinfo['interface_name']
obj = bus.get_object(bus_name, obj_path)

if (method_name != ""):
    methd = obj.get_dbus_method(method_name, intf_name)
    try:
        data = methd(*sys.argv)
        fix_byte(data, None, None)
        pydata = json.loads(json.dumps(data))
        if 'transform' in objinfo:
            objinfo['transform'](pydata)
        printDict("", pydata)
    except Exception as e:
        print e
        r = introspect(bus_name, obj_path, intf_name, method_name)
        if (r == False):
            print "ERROR: Invalid method: " + method_name
        else:
            print "ERROR: Incorrect arguments passed to method"
elif (property_name != ""):
    intf = dbus.Interface(obj, "org.freedesktop.DBus.Properties")
    if (objinfo.has_key('value')):
        property_value = objinfo['value']
    else:
        property_value = eval(sys.argv.pop(0))
    intf.Set(intf_name, property_name, property_value)
else:
    intf = dbus.Interface(obj, "org.freedesktop.DBus.Properties")
    props = intf.GetAll(intf_name)
    for p in props:
        print p + " = " + str(props[p])