<s> from __future__ import absolute_import <EOL> import struct , math <EOL> from . data import * <EOL> from . actions import * <EOL> from . filters import SWFFilterFactory <EOL> from six . moves import range <EOL> from functools import reduce <EOL> class SWFStream ( object ) : <EOL> """<STR_LIT>""" <EOL> FLOAT16_EXPONENT_BASE = <NUM_LIT:15> <EOL> def __init__ ( self , file ) : <EOL> """<STR_LIT>""" <EOL> self . f = file <EOL> self . _bits_pending = <NUM_LIT:0> <EOL> self . _partial_byte = None <EOL> self . _make_masks ( ) <EOL> def bin ( self , s ) : <EOL> """<STR_LIT>""" <EOL> return str ( s ) if s <= <NUM_LIT:1> else bin ( s >> <NUM_LIT:1> ) + str ( s & <NUM_LIT:1> ) <EOL> def calc_max_bits ( self , signed , values ) : <EOL> """<STR_LIT>""" <EOL> b = <NUM_LIT:0> <EOL> vmax = - <NUM_LIT> <EOL> for val in values : <EOL> if signed : <EOL> b = b | val if val >= <NUM_LIT:0> else b | ~ val << <NUM_LIT:1> <EOL> vmax = val if vmax < val else vmax <EOL> else : <EOL> b |= val ; <EOL> bits = <NUM_LIT:0> <EOL> if b > <NUM_LIT:0> : <EOL> bits = len ( self . bin ( b ) ) - <NUM_LIT:2> <EOL> if signed and vmax > <NUM_LIT:0> and len ( self . bin ( vmax ) ) - <NUM_LIT:2> >= bits : <EOL> bits += <NUM_LIT:1> <EOL> return bits <EOL> def close ( self ) : <EOL> """<STR_LIT>""" <EOL> if self . f : <EOL> self . f . close ( ) <EOL> def _make_masks ( self ) : <EOL> self . _masks = [ ( <NUM_LIT:1> << x ) - <NUM_LIT:1> for x in range ( <NUM_LIT:9> ) ] <EOL> def _read_bytes_aligned ( self , bytes ) : <EOL> buf = self . f . read ( bytes ) <EOL> return reduce ( lambda x , y : x << <NUM_LIT:8> | y , buf , <NUM_LIT:0> ) <EOL> def readbits ( self , bits ) : <EOL> """<STR_LIT>""" <EOL> if bits == <NUM_LIT:0> : <EOL> return <NUM_LIT:0> <EOL> if bits % <NUM_LIT:8> == <NUM_LIT:0> and self . _bits_pending == <NUM_LIT:0> : <EOL> return self . _read_bytes_aligned ( bits // <NUM_LIT:8> ) <EOL> out = <NUM_LIT:0> <EOL> masks = self . _masks <EOL> def transfer_bits ( x , y , n , t ) : <EOL> """<STR_LIT>""" <EOL> if n == t : <EOL> return ( x << t ) | y , <NUM_LIT:0> <EOL> mask = masks [ t ] <EOL> remainmask = masks [ n - t ] <EOL> taken = ( ( y >> n - t ) & mask ) <EOL> return ( x << t ) | taken , y & remainmask <EOL> while bits > <NUM_LIT:0> : <EOL> if self . _bits_pending > <NUM_LIT:0> : <EOL> assert self . _partial_byte is not None <EOL> take = min ( self . _bits_pending , bits ) <EOL> out , self . _partial_byte = transfer_bits ( out , self . _partial_byte , self . _bits_pending , take ) <EOL> if take == self . _bits_pending : <EOL> self . _partial_byte = None <EOL> self . _bits_pending -= take <EOL> bits -= take <EOL> continue <EOL> r = self . f . read ( <NUM_LIT:1> ) <EOL> if r == b'<STR_LIT>' : <EOL> raise EOFError <EOL> self . _partial_byte = ord ( r ) <EOL> self . _bits_pending = <NUM_LIT:8> <EOL> return out <EOL> def readFB ( self , bits ) : <EOL> """<STR_LIT>""" <EOL> return float ( self . readSB ( bits ) ) / <NUM_LIT> <EOL> def readSB ( self , bits ) : <EOL> """<STR_LIT>""" <EOL> shift = <NUM_LIT:32> - bits <EOL> return int32 ( self . readbits ( bits ) << shift ) >> shift <EOL> def readUB ( self , bits ) : <EOL> """<STR_LIT>""" <EOL> return self . readbits ( bits ) <EOL> def readSI8 ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) ; <EOL> return struct . unpack ( '<STR_LIT:b>' , self . f . read ( <NUM_LIT:1> ) ) [ <NUM_LIT:0> ] <EOL> def readUI8 ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) ; <EOL> return struct . unpack ( '<STR_LIT:B>' , self . f . read ( <NUM_LIT:1> ) ) [ <NUM_LIT:0> ] <EOL> def readSI16 ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) ; <EOL> return struct . unpack ( '<STR_LIT:h>' , self . f . read ( <NUM_LIT:2> ) ) [ <NUM_LIT:0> ] <EOL> def readUI16 ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) ; <EOL> return struct . unpack ( '<STR_LIT:H>' , self . f . read ( <NUM_LIT:2> ) ) [ <NUM_LIT:0> ] <EOL> def readSI32 ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) ; <EOL> return struct . unpack ( '<STR_LIT>' , self . f . read ( <NUM_LIT:4> ) ) [ <NUM_LIT:0> ] <EOL> def readUI32 ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) ; <EOL> return struct . unpack ( '<STR_LIT>' , self . f . read ( <NUM_LIT:4> ) ) [ <NUM_LIT:0> ] <EOL> def readUI64 ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) ; <EOL> return struct . unpack ( '<STR_LIT>' , self . f . read ( <NUM_LIT:8> ) ) [ <NUM_LIT:0> ] <EOL> def readEncodedU32 ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) ; <EOL> result = self . readUI8 ( ) ; <EOL> if result & <NUM_LIT> != <NUM_LIT:0> : <EOL> result = ( result & <NUM_LIT> ) | ( self . readUI8 ( ) << <NUM_LIT:7> ) <EOL> if result & <NUM_LIT> != <NUM_LIT:0> : <EOL> result = ( result & <NUM_LIT> ) | ( self . readUI8 ( ) << <NUM_LIT> ) <EOL> if result & <NUM_LIT> != <NUM_LIT:0> : <EOL> result = ( result & <NUM_LIT> ) | ( self . readUI8 ( ) << <NUM_LIT> ) <EOL> if result & <NUM_LIT> != <NUM_LIT:0> : <EOL> result = ( result & <NUM_LIT> ) | ( self . readUI8 ( ) << <NUM_LIT> ) <EOL> return result <EOL> def readFLOAT ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) ; <EOL> return struct . unpack ( '<STR_LIT:f>' , self . f . read ( <NUM_LIT:4> ) ) [ <NUM_LIT:0> ] <EOL> def readFLOAT16 ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) <EOL> word = self . readUI16 ( ) <EOL> sign = - <NUM_LIT:1> if ( ( word & <NUM_LIT> ) != <NUM_LIT:0> ) else <NUM_LIT:1> <EOL> exponent = ( word >> <NUM_LIT:10> ) & <NUM_LIT> <EOL> significand = word & <NUM_LIT> <EOL> if exponent == <NUM_LIT:0> : <EOL> if significand == <NUM_LIT:0> : <EOL> return <NUM_LIT:0.0> <EOL> else : <EOL> return sign * math . pow ( <NUM_LIT:2> , <NUM_LIT:1> - SWFStream . FLOAT16_EXPONENT_BASE ) * ( significand / <NUM_LIT> ) <EOL> if exponent == <NUM_LIT> : <EOL> if significand == <NUM_LIT:0> : <EOL> return float ( '<STR_LIT>' ) if sign < <NUM_LIT:0> else float ( '<STR_LIT>' ) <EOL> else : <EOL> return float ( '<STR_LIT>' ) <EOL> return sign * math . pow ( <NUM_LIT:2> , exponent - SWFStream . FLOAT16_EXPONENT_BASE ) * ( <NUM_LIT:1> + significand / <NUM_LIT> ) <EOL> def readFIXED ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) <EOL> return self . readSI32 ( ) / <NUM_LIT> <EOL> def readFIXED8 ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) <EOL> return self . readSI16 ( ) / <NUM_LIT> <EOL> def readCXFORM ( self ) : <EOL> """<STR_LIT>""" <EOL> return SWFColorTransform ( self ) <EOL> def readCXFORMWITHALPHA ( self ) : <EOL> """<STR_LIT>""" <EOL> return SWFColorTransformWithAlpha ( self ) <EOL> def readGLYPHENTRY ( self , glyphBits , advanceBits ) : <EOL> """<STR_LIT>""" <EOL> return SWFGlyphEntry ( self , glyphBits , advanceBits ) <EOL> def readGRADIENT ( self , level = <NUM_LIT:1> ) : <EOL> """<STR_LIT>""" <EOL> return SWFGradient ( self , level ) <EOL> def readFOCALGRADIENT ( self , level = <NUM_LIT:1> ) : <EOL> """<STR_LIT>""" <EOL> return SWFFocalGradient ( self , level ) <EOL> def readGRADIENTRECORD ( self , level = <NUM_LIT:1> ) : <EOL> """<STR_LIT>""" <EOL> return SWFGradientRecord ( self , level ) <EOL> def readKERNINGRECORD ( self , wideCodes ) : <EOL> """<STR_LIT>""" <EOL> return SWFKerningRecord ( self , wideCodes ) <EOL> def readLANGCODE ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) <EOL> return self . readUI8 ( ) <EOL> def readMATRIX ( self ) : <EOL> """<STR_LIT>""" <EOL> return SWFMatrix ( self ) <EOL> def readRECT ( self ) : <EOL> """<STR_LIT>""" <EOL> r = SWFRectangle ( ) <EOL> r . parse ( self ) <EOL> return r <EOL> def readSHAPE ( self , unit_divisor = <NUM_LIT:20> ) : <EOL> """<STR_LIT>""" <EOL> return SWFShape ( self , <NUM_LIT:1> , unit_divisor ) <EOL> def readSHAPEWITHSTYLE ( self , level = <NUM_LIT:1> , unit_divisor = <NUM_LIT:20> ) : <EOL> """<STR_LIT>""" <EOL> return SWFShapeWithStyle ( self , level , unit_divisor ) <EOL> def readCURVEDEDGERECORD ( self , num_bits ) : <EOL> """<STR_LIT>""" <EOL> return SWFShapeRecordCurvedEdge ( self , num_bits ) <EOL> def readSTRAIGHTEDGERECORD ( self , num_bits ) : <EOL> """<STR_LIT>""" <EOL> return SWFShapeRecordStraightEdge ( self , num_bits ) <EOL> def readSTYLECHANGERECORD ( self , states , fill_bits , line_bits , level = <NUM_LIT:1> ) : <EOL> """<STR_LIT>""" <EOL> return SWFShapeRecordStyleChange ( self , states , fill_bits , line_bits , level ) <EOL> def readFILLSTYLE ( self , level = <NUM_LIT:1> ) : <EOL> """<STR_LIT>""" <EOL> return SWFFillStyle ( self , level ) <EOL> def readTEXTRECORD ( self , glyphBits , advanceBits , previousRecord = None , level = <NUM_LIT:1> ) : <EOL> """<STR_LIT>""" <EOL> if self . readUI8 ( ) == <NUM_LIT:0> : <EOL> return None <EOL> else : <EOL> self . seek ( self . tell ( ) - <NUM_LIT:1> ) <EOL> return SWFTextRecord ( self , glyphBits , advanceBits , previousRecord , level ) <EOL> def readLINESTYLE ( self , level = <NUM_LIT:1> ) : <EOL> """<STR_LIT>""" <EOL> return SWFLineStyle ( self , level ) <EOL> def readLINESTYLE2 ( self , level = <NUM_LIT:1> ) : <EOL> """<STR_LIT>""" <EOL> return SWFLineStyle2 ( self , level ) <EOL> def readMORPHFILLSTYLE ( self , level = <NUM_LIT:1> ) : <EOL> """<STR_LIT>""" <EOL> return SWFMorphFillStyle ( self , level ) <EOL> def readMORPHLINESTYLE ( self , level = <NUM_LIT:1> ) : <EOL> """<STR_LIT>""" <EOL> return SWFMorphLineStyle ( self , level ) <EOL> def readMORPHLINESTYLE2 ( self , level = <NUM_LIT:1> ) : <EOL> """<STR_LIT>""" <EOL> return SWFMorphLineStyle2 ( self , level ) <EOL> def readMORPHGRADIENT ( self , level = <NUM_LIT:1> ) : <EOL> """<STR_LIT>""" <EOL> return SWFMorphGradient ( self , level ) <EOL> def readMORPHGRADIENTRECORD ( self ) : <EOL> """<STR_LIT>""" <EOL> return SWFMorphGradientRecord ( self ) <EOL> def readACTIONRECORD ( self ) : <EOL> """<STR_LIT>""" <EOL> action = None <EOL> actionCode = self . readUI8 ( ) <EOL> if actionCode != <NUM_LIT:0> : <EOL> actionLength = self . readUI16 ( ) if actionCode >= <NUM_LIT> else <NUM_LIT:0> <EOL> action = SWFActionFactory . create ( actionCode , actionLength ) <EOL> action . parse ( self ) <EOL> return action <EOL> def readACTIONRECORDs ( self ) : <EOL> """<STR_LIT>""" <EOL> out = [ ] <EOL> while <NUM_LIT:1> : <EOL> action = self . readACTIONRECORD ( ) <EOL> if action : <EOL> out . append ( action ) <EOL> else : <EOL> break <EOL> return out <EOL> def readCLIPACTIONS ( self , version ) : <EOL> """<STR_LIT>""" <EOL> return SWFClipActions ( self , version ) <EOL> def readCLIPACTIONRECORD ( self , version ) : <EOL> """<STR_LIT>""" <EOL> pos = self . tell ( ) <EOL> flags = self . readUI32 ( ) if version >= <NUM_LIT:6> else self . readUI16 ( ) <EOL> if flags == <NUM_LIT:0> : <EOL> return None <EOL> else : <EOL> self . seek ( pos ) <EOL> return SWFClipActionRecord ( self , version ) <EOL> def readCLIPEVENTFLAGS ( self , version ) : <EOL> """<STR_LIT>""" <EOL> return SWFClipEventFlags ( self , version ) <EOL> def readRGB ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) ; <EOL> r = self . readUI8 ( ) <EOL> g = self . readUI8 ( ) <EOL> b = self . readUI8 ( ) <EOL> return ( <NUM_LIT> << <NUM_LIT> ) | ( r << <NUM_LIT:16> ) | ( g << <NUM_LIT:8> ) | b <EOL> def readRGBA ( self ) : <EOL> """<STR_LIT>""" <EOL> self . reset_bits_pending ( ) ; <EOL> r = self . readUI8 ( ) <EOL> g = self . readUI8 ( ) <EOL> b = self . readUI8 ( ) <EOL> a = self . readUI8 ( ) <EOL> return ( a << <NUM_LIT> ) | ( r << <NUM_LIT:16> ) | ( g << <NUM_LIT:8> ) | b <EOL> def readSYMBOL ( self ) : <EOL> """<STR_LIT>""" <EOL> return SWFSymbol ( self ) <EOL> def readString ( self ) : <EOL> """<STR_LIT>""" <EOL> s = self . f . read ( <NUM_LIT:1> ) <EOL> string = b"<STR_LIT>" <EOL> while ord ( s ) > <NUM_LIT:0> : <EOL> string += s <EOL> s = self . f . read ( <NUM_LIT:1> ) <EOL> return string . decode ( ) <EOL> def readFILTER ( self ) : <EOL> """<STR_LIT>""" <EOL> filterId = self . readUI8 ( ) <EOL> filter = SWFFilterFactory . create ( filterId ) <EOL> filter . parse ( self ) <EOL> return filter <EOL> def readFILTERLIST ( self ) : <EOL> """<STR_LIT>""" <EOL> number = self . readUI8 ( ) <EOL> return [ self . readFILTER ( ) for _ in range ( number ) ] <EOL> def readZONEDATA ( self ) : <EOL> """<STR_LIT>""" <EOL> return SWFZoneData ( self ) <EOL> def readZONERECORD ( self ) : <EOL> """<STR_LIT>""" <EOL> return SWFZoneRecord ( self ) <EOL> def readSOUNDINFO ( self ) : <EOL> """<STR_LIT>""" <EOL> return SWFSoundInfo ( self ) <EOL> def readSOUNDENVELOPE ( self ) : <EOL> """<STR_LIT>""" <EOL> return SWFSoundEnvelope ( self ) <EOL> def readBUTTONRECORD ( self , version ) : <EOL> rc = SWFButtonRecord ( data = self , version = version ) <EOL> return rc if rc . valid else None <EOL> def readBUTTONRECORDs ( self , version ) : <EOL> """<STR_LIT>""" <EOL> out = [ ] <EOL> while <NUM_LIT:1> : <EOL> button = self . readBUTTONRECORD ( version ) <EOL> if button : <EOL> out . append ( button ) <EOL> else : <EOL> break <EOL> return out <EOL> def readBUTTONCONDACTION ( self ) : <EOL> """<STR_LIT>""" <EOL> size = self . readUI16 ( ) <EOL> if size == <NUM_LIT:0> : <EOL> return None <EOL> return SWFButtonCondAction ( self ) <EOL> def readBUTTONCONDACTIONSs ( self ) : <EOL> """<STR_LIT>""" <EOL> out = [ ] <EOL> while <NUM_LIT:1> : <EOL> action = self . readBUTTONCONDACTION ( ) <EOL> if action : <EOL> out . append ( action ) <EOL> else : <EOL> break <EOL> return out <EOL> def readEXPORT ( self ) : <EOL> """<STR_LIT>""" <EOL> return SWFExport ( self ) <EOL> def readMORPHFILLSTYLEARRAY ( self ) : <EOL> count = self . readUI8 ( ) <EOL> if count == <NUM_LIT> : <EOL> count = self . readUI16 ( ) <EOL> return [ self . readMORPHFILLSTYLE ( ) for _ in range ( count ) ] <EOL> def readMORPHLINESTYLEARRAY ( self , version ) : <EOL> count = self . readUI8 ( ) <EOL> if count == <NUM_LIT> : <EOL> count = self . readUI16 ( ) <EOL> kind = self . readMORPHLINESTYLE if version == <NUM_LIT:1> else self . readMORPHLINESTYLE2 <EOL> return [ kind ( ) for _ in range ( count ) ] <EOL> def readraw_tag ( self ) : <EOL> """<STR_LIT>""" <EOL> return SWFRawTag ( self ) <EOL> def readtag_header ( self ) : <EOL> """<STR_LIT>""" <EOL> pos = self . tell ( ) <EOL> tag_type_and_length = self . readUI16 ( ) <EOL> tag_length = tag_type_and_length & <NUM_LIT> <EOL> if tag_length == <NUM_LIT> : <EOL> tag_length = self . readSI32 ( ) ; <EOL> return SWFRecordHeader ( tag_type_and_length >> <NUM_LIT:6> , tag_length , self . tell ( ) - pos ) <EOL> def skip_bytes ( self , length ) : <EOL> """<STR_LIT>""" <EOL> self . f . seek ( self . tell ( ) + length ) <EOL> def reset_bits_pending ( self ) : <EOL> """<STR_LIT>""" <EOL> self . _bits_pending = <NUM_LIT:0> <EOL> def read ( self , count = <NUM_LIT:0> ) : <EOL> """<STR_LIT>""" <EOL> return self . f . read ( count ) if count > <NUM_LIT:0> else self . f . read ( ) <EOL> def seek ( self , pos , whence = <NUM_LIT:0> ) : <EOL> """<STR_LIT>""" <EOL> self . f . seek ( pos , whence ) <EOL> def tell ( self ) : <EOL> """<STR_LIT>""" <EOL> return self . f . tell ( ) <EOL> def int32 ( x ) : <EOL> """<STR_LIT>""" <EOL> if x > <NUM_LIT> : <EOL> raise OverflowError <EOL> if x > <NUM_LIT> : <EOL> x = int ( <NUM_LIT> - x ) <EOL> if x < <NUM_LIT> : <EOL> return - x <EOL> else : <EOL> return - <NUM_LIT> <EOL> return x </s>
