def listen(self, xid, pipe=None, timeout=10.0): if pipe is None: pipe = self.c1 header, data = pipe.listen(xid, timeout) if data: p = nfs4lib.FancyNFS4Unpacker(data) data = p.unpack_COMPOUND4res() return data
def __init__(self, rootfh, host, port, pubfh = None): rpc.RPCServer.__init__(self, prog=NFS4_PROGRAM, vers=NFS_V4, host=host, port=port) self.nfs4packer = nfs4lib.FancyNFS4Packer() self.nfs4unpacker = nfs4lib.FancyNFS4Unpacker('') self.state = nfs4state.NFSServerState(rootfh) self.fhcache = {} self.rootfh = rootfh self.pubfh = pubfh self.verfnum = 0
def handle_1(self, data, cred): log_cb.info("*" * 20) log_cb.info("Handling COMPOUND") # data is an XDR packed string. Unpack it. unpacker = nfs4lib.FancyNFS4Unpacker(data) try: args = unpacker.unpack_CB_COMPOUND4args() unpacker.done() except: log_cb.warn("returning GARBAGE_ARGS") log_cb.debug("unpacking raised the following error", exc_info=True) return rpc.GARBAGE_ARGS, None log_cb.debug(repr(args)) try: # SEQUENCE needs to know size of request args.req_size = len(data) # Handle the request env = self.op_cb_compound(args, cred) log_cb.info(repr(env.results.reply.results)) # Pack the results back into an XDR string p = nfs4lib.FancyNFS4Packer() p.pack_CB_COMPOUND4res( CB_COMPOUND4res(env.results.reply.status, env.results.reply.tag, env.results.reply.results)) data = p.get_buffer() # Stuff the replay cache if env.cache is not None: p.reset() p.pack_CB_COMPOUND4res( CB_COMPOUND4res(env.results.cache.status, env.results.cache.tag, env.results.cache.results)) env.cache.data = p.get_buffer() env.cache.valid.set() except NFS4Replay as e: log_cb.info("Replay...waiting for valid data") e.cache.valid.wait() log_cb.info("Replay...sending data") data = e.cache.data return rpc.SUCCESS, data, getattr(env, "notify", None)
def handle_1(self, data, cred, callback=False): """COMPOUND procedure""" log.debug("*" * 40) if callback: log.debug("** CALLBACK **") log.debug("Handling COMPOUND") # stage 1: data in XDR as received from the client unpacker = nfs4lib.FancyNFS4Unpacker(data) if callback: args = unpacker.unpack_CB_COMPOUNDargs() else: args = unpacker.unpack_COMPOUND4args() log.debug("Client sent:") log.debug(repr(args)) unpacker.done() # stage 2: pre-processing - data in COMPOUND4args # XXX: check operation, alter stuff, delay etc. etc. args.req_size = len(data) # BUG, need to use cred.payload_size if callback: env = CBCompoundState(args, cred) else: env = CompoundState(args, cred) for arg in args.argarray: env.index += 1 opname = nfs_opnum4.get(arg.argop, 'op_illegal') log.info("*** %s (%d) ***" % (opname, arg.argop)) # look for functions implemented by the proxy # that override communication funct = getattr(self, opname.lower(), None) if funct is not None and callable(funct): try: result = funct(arg, cred, direction=0) except Exception: log.error("Function override %s failed" % opname.lower()) # handle error condition if specified error = None if self.errorhandler is not None: error = self.errorhandler.get_error(opname.lower()[3:], arg, env) if error is not None: result = encode_status_by_name(opname.lower()[3:], int(error), msg="Proxy Rewrite Error") env.results.append(result) p = nfs4lib.FancyNFS4Packer() if callback: res = CB_COMPOUND4res(env.results.reply.status, env.results.reply.tag, env.results.reply.results) p.pack_CB_COMPOUND4res(res) else: res = COMPOUND4res(env.results.reply.status, env.results.reply.tag, env.results.reply.results) p.pack_COMPOUND4res(res) log.info(repr(res)) reply = p.get_buffer() return rpc.SUCCESS, reply #stage 3: repack the data and forward to server packer = nfs4lib.FancyNFS4Packer() if callback: packer.pack_CB_COMPOUND4args(args) else: packer.pack_COMPOUND4args(args) log.debug("Proxy sent:") log.debug(repr(args)) calldata = packer.get_buffer() try: ret_data = self.forward_call(calldata, callback) except rpc.RPCTimeout: log.critical("Error: cannot connect to destination server") return rpc.GARBAGE_ARGS, None # stage 4: data in XDR as returned by the server unpacker = nfs4lib.FancyNFS4Unpacker(ret_data) if callback: res = unpacker.unpack_CB_COMPOUND4res() else: res = unpacker.unpack_COMPOUND4res() log.debug("Server returned:") log.debug(repr(res)) unpacker.done() # stage 5: post-processing - data in COMPOUND4res # XXX: check operation etc. for arg in res.resarray: opname = nfs_opnum4.get(arg.resop, 'op_illegal') log.info("*** %s (%d) ***" % (opname, arg.resop)) # look for functions implemented by the proxy # that override communication funct = getattr(self, opname.lower(), None) if funct is not None and callable(funct): try: result = funct(arg, cred, direction=1) except Exception: log.error("Function override %s failed" % opname.lower()) # state 6: repack and return XDR data to client packer = nfs4lib.FancyNFS4Packer() if callback: packer.pack_CB_COMPOUND4res(res) else: packer.pack_COMPOUND4res(res) log.debug("Proxy returned:") log.debug(repr(res)) reply = packer.get_buffer() return rpc.SUCCESS, reply