--- /dev/null
+"""\r
+shared types, functions and constants\r
+"""\r
+import sys\r
+\r
+\r
+DEFAULT_PORT = 18812\r
+\r
+def raise_exception(typ, val, tbtext):\r
+ """a helper for raising remote exceptions"""\r
+ if type(typ) == str:\r
+ raise typ\r
+ else:\r
+ val._remote_traceback = tbtext\r
+ raise val\r
+\r
+class ImmDict(object):\r
+ """immutable dict (passes by value)"""\r
+ def __init__(self, dict):\r
+ self.dict = dict\r
+ def items(self):\r
+ return self.dict.items()\r
+\r
+class AttrFrontend(object):\r
+ """a wrapper that implements the attribute protocol for a dict backend"""\r
+ def __init__(self, dict):\r
+ self.__dict__["____dict"] = dict\r
+ def __delattr__(self, name):\r
+ del self.__dict__["____dict"][name]\r
+ def __getattr__(self, name):\r
+ return self.__dict__["____dict"][name]\r
+ def __setattr__(self, name, value):\r
+ self.__dict__["____dict"][name] = value\r
+ def __repr__(self):\r
+ return "<AttrFrontend %s>" % (self.__dict__["____dict"].keys(),)\r
+\r
+# installs an rpyc-enabled exception hook. this happens automatically when the module\r
+# is imported. also, make sure the current excepthook is the original one, so we dont \r
+# install our hook twice (and thus cause infinite recursion) in case the module is reloaded \r
+def rpyc_excepthook(exctype, value, traceback):\r
+ if hasattr(value, "_remote_traceback"):\r
+ print >> sys.stderr, "======= Remote traceback ======="\r
+ print >> sys.stderr, value._remote_traceback\r
+ print >> sys.stderr, "======= Local exception ======="\r
+ orig_excepthook(exctype, value, traceback)\r
+ else:\r
+ orig_excepthook(exctype, value, traceback)\r
+\r
+if sys.excepthook.__name__ != "rpyc_excepthook": \r
+ orig_excepthook = sys.excepthook\r
+ sys.excepthook = rpyc_excepthook\r
+\r
+\r