protolib.py revision 10107
110107Sradhika.jagtap@ARM.com#!/usr/bin/env python
210107Sradhika.jagtap@ARM.com
310107Sradhika.jagtap@ARM.com# Copyright (c) 2013 ARM Limited
410107Sradhika.jagtap@ARM.com# All rights reserved
510107Sradhika.jagtap@ARM.com#
610107Sradhika.jagtap@ARM.com# The license below extends only to copyright in the software and shall
710107Sradhika.jagtap@ARM.com# not be construed as granting a license to any other intellectual
810107Sradhika.jagtap@ARM.com# property including but not limited to intellectual property relating
910107Sradhika.jagtap@ARM.com# to a hardware implementation of the functionality of the software
1010107Sradhika.jagtap@ARM.com# licensed hereunder.  You may use the software subject to the license
1110107Sradhika.jagtap@ARM.com# terms below provided that you ensure that this notice is replicated
1210107Sradhika.jagtap@ARM.com# unmodified and in its entirety in all distributions of the software,
1310107Sradhika.jagtap@ARM.com# modified or unmodified, in source code or in binary form.
1410107Sradhika.jagtap@ARM.com#
1510107Sradhika.jagtap@ARM.com# Redistribution and use in source and binary forms, with or without
1610107Sradhika.jagtap@ARM.com# modification, are permitted provided that the following conditions are
1710107Sradhika.jagtap@ARM.com# met: redistributions of source code must retain the above copyright
1810107Sradhika.jagtap@ARM.com# notice, this list of conditions and the following disclaimer;
1910107Sradhika.jagtap@ARM.com# redistributions in binary form must reproduce the above copyright
2010107Sradhika.jagtap@ARM.com# notice, this list of conditions and the following disclaimer in the
2110107Sradhika.jagtap@ARM.com# documentation and/or other materials provided with the distribution;
2210107Sradhika.jagtap@ARM.com# neither the name of the copyright holders nor the names of its
2310107Sradhika.jagtap@ARM.com# contributors may be used to endorse or promote products derived from
2410107Sradhika.jagtap@ARM.com# this software without specific prior written permission.
2510107Sradhika.jagtap@ARM.com#
2610107Sradhika.jagtap@ARM.com# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
2710107Sradhika.jagtap@ARM.com# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
2810107Sradhika.jagtap@ARM.com# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
2910107Sradhika.jagtap@ARM.com# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
3010107Sradhika.jagtap@ARM.com# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
3110107Sradhika.jagtap@ARM.com# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
3210107Sradhika.jagtap@ARM.com# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
3310107Sradhika.jagtap@ARM.com# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
3410107Sradhika.jagtap@ARM.com# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
3510107Sradhika.jagtap@ARM.com# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
3610107Sradhika.jagtap@ARM.com# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
3710107Sradhika.jagtap@ARM.com#
3810107Sradhika.jagtap@ARM.com# Copyright 2008 Google Inc.  All rights reserved.
3910107Sradhika.jagtap@ARM.com# http://code.google.com/p/protobuf/
4010107Sradhika.jagtap@ARM.com#
4110107Sradhika.jagtap@ARM.com# Redistribution and use in source and binary forms, with or without
4210107Sradhika.jagtap@ARM.com# modification, are permitted provided that the following conditions are
4310107Sradhika.jagtap@ARM.com# met:
4410107Sradhika.jagtap@ARM.com#
4510107Sradhika.jagtap@ARM.com#     * Redistributions of source code must retain the above copyright
4610107Sradhika.jagtap@ARM.com# notice, this list of conditions and the following disclaimer.
4710107Sradhika.jagtap@ARM.com#     * Redistributions in binary form must reproduce the above
4810107Sradhika.jagtap@ARM.com# copyright notice, this list of conditions and the following disclaimer
4910107Sradhika.jagtap@ARM.com# in the documentation and/or other materials provided with the
5010107Sradhika.jagtap@ARM.com# distribution.
5110107Sradhika.jagtap@ARM.com#     * Neither the name of Google Inc. nor the names of its
5210107Sradhika.jagtap@ARM.com# contributors may be used to endorse or promote products derived from
5310107Sradhika.jagtap@ARM.com# this software without specific prior written permission.
5410107Sradhika.jagtap@ARM.com#
5510107Sradhika.jagtap@ARM.com# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
5610107Sradhika.jagtap@ARM.com# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
5710107Sradhika.jagtap@ARM.com# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
5810107Sradhika.jagtap@ARM.com# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
5910107Sradhika.jagtap@ARM.com# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
6010107Sradhika.jagtap@ARM.com# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
6110107Sradhika.jagtap@ARM.com# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
6210107Sradhika.jagtap@ARM.com# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
6310107Sradhika.jagtap@ARM.com# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
6410107Sradhika.jagtap@ARM.com# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
6510107Sradhika.jagtap@ARM.com# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
6610107Sradhika.jagtap@ARM.com#
6710107Sradhika.jagtap@ARM.com# Authors: Andreas Hansson
6810107Sradhika.jagtap@ARM.com#          Radhika Jagtap
6910107Sradhika.jagtap@ARM.com
7010107Sradhika.jagtap@ARM.com# This file is a library of commonly used functions used when interfacing
7110107Sradhika.jagtap@ARM.com# with protobuf python messages. For eg, the decode scripts for different
7210107Sradhika.jagtap@ARM.com# types of proto objects can use the same function to decode a single message
7310107Sradhika.jagtap@ARM.com
7410107Sradhika.jagtap@ARM.comimport struct
7510107Sradhika.jagtap@ARM.com
7610107Sradhika.jagtap@ARM.comdef DecodeVarint(in_file):
7710107Sradhika.jagtap@ARM.com    """
7810107Sradhika.jagtap@ARM.com    The decoding of the Varint32 is copied from
7910107Sradhika.jagtap@ARM.com    google.protobuf.internal.decoder and is only repeated here to
8010107Sradhika.jagtap@ARM.com    avoid depending on the internal functions in the library. If the
8110107Sradhika.jagtap@ARM.com    end of file is reached, return (0, 0).
8210107Sradhika.jagtap@ARM.com    """
8310107Sradhika.jagtap@ARM.com    result = 0
8410107Sradhika.jagtap@ARM.com    shift = 0
8510107Sradhika.jagtap@ARM.com    pos = 0
8610107Sradhika.jagtap@ARM.com    # Use a 32-bit mask
8710107Sradhika.jagtap@ARM.com    mask = 0xffffffff
8810107Sradhika.jagtap@ARM.com    while 1:
8910107Sradhika.jagtap@ARM.com        c = in_file.read(1)
9010107Sradhika.jagtap@ARM.com        if len(c) == 0:
9110107Sradhika.jagtap@ARM.com            return (0, 0)
9210107Sradhika.jagtap@ARM.com        b = struct.unpack('<B', c)[0]
9310107Sradhika.jagtap@ARM.com        result |= ((b & 0x7f) << shift)
9410107Sradhika.jagtap@ARM.com        pos += 1
9510107Sradhika.jagtap@ARM.com        if not (b & 0x80):
9610107Sradhika.jagtap@ARM.com            if result > 0x7fffffffffffffff:
9710107Sradhika.jagtap@ARM.com                result -= (1 << 64)
9810107Sradhika.jagtap@ARM.com                result |= ~mask
9910107Sradhika.jagtap@ARM.com            else:
10010107Sradhika.jagtap@ARM.com                result &= mask
10110107Sradhika.jagtap@ARM.com                return (result, pos)
10210107Sradhika.jagtap@ARM.com            shift += 7
10310107Sradhika.jagtap@ARM.com            if shift >= 64:
10410107Sradhika.jagtap@ARM.com                raise IOError('Too many bytes when decoding varint.')
10510107Sradhika.jagtap@ARM.com
10610107Sradhika.jagtap@ARM.comdef decodeMessage(in_file, message):
10710107Sradhika.jagtap@ARM.com    """
10810107Sradhika.jagtap@ARM.com    Attempt to read a message from the file and decode it. Return
10910107Sradhika.jagtap@ARM.com    False if no message could be read.
11010107Sradhika.jagtap@ARM.com    """
11110107Sradhika.jagtap@ARM.com    try:
11210107Sradhika.jagtap@ARM.com        size, pos = DecodeVarint(in_file)
11310107Sradhika.jagtap@ARM.com        if size == 0:
11410107Sradhika.jagtap@ARM.com            return False
11510107Sradhika.jagtap@ARM.com        buf = in_file.read(size)
11610107Sradhika.jagtap@ARM.com        message.ParseFromString(buf)
11710107Sradhika.jagtap@ARM.com        return True
11810107Sradhika.jagtap@ARM.com    except IOError:
11910107Sradhika.jagtap@ARM.com        return False
12010107Sradhika.jagtap@ARM.com
12110107Sradhika.jagtap@ARM.comdef EncodeVarint(out_file, value):
12210107Sradhika.jagtap@ARM.com  """
12310107Sradhika.jagtap@ARM.com  The encoding of the Varint32 is copied from
12410107Sradhika.jagtap@ARM.com  google.protobuf.internal.encoder and is only repeated here to
12510107Sradhika.jagtap@ARM.com  avoid depending on the internal functions in the library.
12610107Sradhika.jagtap@ARM.com  """
12710107Sradhika.jagtap@ARM.com  bits = value & 0x7f
12810107Sradhika.jagtap@ARM.com  value >>= 7
12910107Sradhika.jagtap@ARM.com  while value:
13010107Sradhika.jagtap@ARM.com    out_file.write(struct.pack('<B', 0x80|bits))
13110107Sradhika.jagtap@ARM.com    bits = value & 0x7f
13210107Sradhika.jagtap@ARM.com    value >>= 7
13310107Sradhika.jagtap@ARM.com  out_file.write(struct.pack('<B', bits))
13410107Sradhika.jagtap@ARM.com
13510107Sradhika.jagtap@ARM.comdef encodeMessage(out_file, message):
13610107Sradhika.jagtap@ARM.com    """
13710107Sradhika.jagtap@ARM.com    Encoded a message with the length prepended as a 32-bit varint.
13810107Sradhika.jagtap@ARM.com    """
13910107Sradhika.jagtap@ARM.com    out = message.SerializeToString()
14010107Sradhika.jagtap@ARM.com    EncodeVarint(out_file, len(out))
14110107Sradhika.jagtap@ARM.com    out_file.write(out)
142