From 589deb9fe14baa8e07d661d4e3d3a60c48512545 Mon Sep 17 00:00:00 2001 From: Aldo Cortesi Date: Mon, 4 May 2015 10:48:35 +1200 Subject: websockets: specification of fin, mask, rsv1-3 bits. --- libpathod/language/base.py | 29 ++++++++++- libpathod/language/websockets.py | 69 ++++++++++++++++++++++++--- libpathod/templates/docs_lang_websockets.html | 40 +++++++++++++++- 3 files changed, 128 insertions(+), 10 deletions(-) (limited to 'libpathod') diff --git a/libpathod/language/base.py b/libpathod/language/base.py index 725a0d42..4179fa7d 100644 --- a/libpathod/language/base.py +++ b/libpathod/language/base.py @@ -224,7 +224,6 @@ class _Component(Token): A value component of the primary specification of an message. Components produce byte values desribe the bytes of the message. """ - @abc.abstractmethod def values(self, settings): # pragma: no cover """ A sequence of values, which can either be strings or generators. @@ -376,6 +375,34 @@ class Value(_Component): return self.__class__(self.value.freeze(settings)) +class Boolean(_Component): + """ + A boolean flag. + name = true + -name = false + """ + name = "" + + def __init__(self, value): + self.value = value + + @classmethod + def expr(klass): + e = pp.Optional(pp.Literal("-"), default=True) + e += pp.Literal(klass.name).suppress() + + def parse(s, loc, toks): + val = True + if toks[0] == "-": + val = False + return klass(val) + + return e.setParseAction(parse) + + def spec(self): + return "%s%s"%("-" if not self.value else "", self.name) + + class IntField(_Component): """ An integer field, where values can optionally specified by name. diff --git a/libpathod/language/websockets.py b/libpathod/language/websockets.py index ddffdab9..4b8a8148 100644 --- a/libpathod/language/websockets.py +++ b/libpathod/language/websockets.py @@ -17,7 +17,7 @@ class WF(base.CaselessLiteral): TOK = "wf" -class Code(base.IntField): +class OpCode(base.IntField): names = { "continue": netlib.websockets.OPCODE.CONTINUE, "text": netlib.websockets.OPCODE.TEXT, @@ -34,13 +34,46 @@ class Body(base.Value): preamble = "b" +class Raw(base.CaselessLiteral): + TOK = "r" + + +class Fin(base.Boolean): + name = "fin" + + +class RSV1(base.Boolean): + name = "rsv1" + + +class RSV2(base.Boolean): + name = "rsv2" + + +class RSV3(base.Boolean): + name = "rsv3" + + +class Mask(base.Boolean): + name = "mask" + + class WebsocketFrame(message.Message): comps = ( Body, - Code, + + OpCode, + # Bit flags + Fin, + RSV1, + RSV2, + RSV3, + Mask, actions.PauseAt, actions.DisconnectAt, - actions.InjectAt + actions.InjectAt, + + Raw, ) logattrs = ["body"] @property @@ -52,8 +85,28 @@ class WebsocketFrame(message.Message): return self.tok(Body) @property - def code(self): - return self.tok(Code) + def opcode(self): + return self.tok(OpCode) + + @property + def fin(self): + return self.tok(Fin) + + @property + def rsv1(self): + return self.tok(RSV1) + + @property + def rsv2(self): + return self.tok(RSV2) + + @property + def rsv3(self): + return self.tok(RSV3) + + @property + def mask(self): + return self.tok(Mask) @classmethod def expr(klass): @@ -81,8 +134,10 @@ class WebsocketFrame(message.Message): mask = True, payload_length = length ) - if self.code: - frameparts["opcode"] = self.code.value + for i in ["opcode", "fin", "rsv1", "rsv2", "rsv3", "mask"]: + v = getattr(self, i, None) + if v is not None: + frameparts[i] = v.value frame = netlib.websockets.FrameHeader(**frameparts) vals = [frame.to_bytes()] if self.body: diff --git a/libpathod/templates/docs_lang_websockets.html b/libpathod/templates/docs_lang_websockets.html index c414320c..9b595e74 100644 --- a/libpathod/templates/docs_lang_websockets.html +++ b/libpathod/templates/docs_lang_websockets.html @@ -16,9 +16,45 @@ Set the op code. This can either be an integer from 0-15, or be - one of the following opcode names: continue, - text, binary, close, ping, + one of the following opcode names: text (the default), + continue, binary, close, ping, pong. + + + + + + [-]fin + + Set or un-set the fin bit. + + + + + [-]rsv1 + + Set or un-set the rsv1 bit. + + + + + [-]rsv2 + + Set or un-set the rsv2 bit. + + + + + [-]rsv3 + + Set or un-set the rsv3 bit. + + + + + [-]mask + + Set or un-set the mask bit. -- cgit v1.2.3