""" Backend superclass for assembler/disassembler - handles common functions. :author: Ben Cheney :license: MIT """ from __future__ import absolute_import from cmd import Cmd import logging from chiasm_shell.config import get_backends l = logging.getLogger('chiasm_shell.backend') class Backend(Cmd): """ Backend - common functions shared by both assembler and disassembler. """ def __init__(self): """ Create a new Backend instance. """ Cmd.__init__(self) self._init_backend() self.launch_module = None def _init_backend(self): """ _init_backend is responsible for setting the prompt """ raise NotImplementedError("Backends need to implement _init_backend") def clear_state(self): """ Optional interface to reset internal backend state. """ pass def default(self, line): raise NotImplementedError("Backends need to implement default hanlders") def get_arch(self): """ Optional interface to display the current architecture. """ pass def do_quit(self, dummy_args): """ Quits chiasm shell - return to system prompt. """ raise SystemExit def do_exit(self, dummy_args): """ Quits chiasm shell - return to system prompt. """ raise SystemExit def cmdloop(self, intro=None): """ Overridden cmdloop to catch CTRL-Cs """ try: Cmd.cmdloop(self, intro) except KeyboardInterrupt: l.info("type \'quit\' or \'exit\' to exit") self.cmdloop() def do_switch(self, arg): """ Switch to another chiasm backend (type lsbackends to see what's available). """ if arg.strip() == '': l.error("usage: switch <backend>") return False backends = get_backends() if arg in backends: new_backend = backends[arg] new_backend.clear_state() self.launch_module = backends[arg] return True # True = quit this backend's loop else: l.error("backend %s not found", arg) self.launch_module = None def do_lsbackends(self, dummy_args): """ List the chiasm backends currently available. """ l.info(", ".join(get_backends().keys())) def postcmd(self, stop, line): """ Just overridden for debugging purposes. """ l.debug("i'm in postcmd, line is %s", line) return stop