Skip to content

Commit

Permalink
A start at pythoncardx.framework.tlv. Note toBytes: the function both…
Browse files Browse the repository at this point in the history
… static and not static !
  • Loading branch information
benallard committed Sep 20, 2011
1 parent ddab8d1 commit 4c500d3
Show file tree
Hide file tree
Showing 3 changed files with 110 additions and 17 deletions.
6 changes: 4 additions & 2 deletions pythoncardx/framework/tlv/__init__.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
from javacard.framework import CardRuntimeException
from pythoncard.framework import CardRuntimeException

class TLVException(CardRuntimeException):
EMPTY_TAG = 0
Expand All @@ -13,6 +13,8 @@ class TLVException(CardRuntimeException):
TLV_LENGTH_GREATER_THAN_32767 = 9
TLV_SIZE_GREATER_THAN_32767 = 10

from pythoncard.framework.tlv import bertag
from pythoncardx.framework.tlv import bertag

BERTag = bertag.BERTag
PrimitiveBERTag = bertag.PrimitiveBERTag
ConstructedBERTag = bertag.ConstructedBERTag
106 changes: 91 additions & 15 deletions pythoncardx/framework/tlv/bertag.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,11 @@
"""
It's 2.2 ... not that prioritary ...
"""
from pythoncardx.framework.tlv import TLVException

class toBytes(object):
def __get__(self, obj, objtype=None):
if obj is not None:
return obj._toBytesBound
else:
return BERTag._toBytesStatic

class BERTag(object):
BER_TAG_CLASS_MASK_APPLICATION = 0
Expand All @@ -11,16 +16,87 @@ class BERTag(object):
BER_TAG_TYPE_PRIMITIVE = 5

def __init__(self):
self._tag = 0
self._length = 0
self._value = []

def equals(self, otherTag):
pass

@classmethod
def getInstance(classs, bArray, bOff):
c = classs()
c.init(bArray, bOff)
return c
self._tagClass = 0
self._tagNumber = 0

def init(self, bArray, bOff):
self._tagClass = bArray[bOff] >> 6
if (bArray[bOff] & 0x1f) == 0x1f:
self._tagNumber = 0
bOff += 1
while (bArray[bOff] & 0x80) == 0x80:
self._tagNumber = self._tagNumber << 7
self._tagNumber += bArray[bOff] & 0x7f
bOff += 1
self._tagNumber = self._tagNumber << 7
self._tagNumber += bArray[bOff] & 0x7f
else:
self._tagNumber = bArray[bOff] & 0x1f

def _toBytesBound(self, outBuf, bOffset):
outBuf[bOffset] = self._tagClass << 6
outBuf[bOffset] += self._PC << 5
if self._tagNumber <= 30:
outBuf[bOffset] += self._tagNumber
return 1
else:
tagNumber = self._tagNumber
outBuf[bOffset] += 0x1f
chunks = []
while tagNumber > 0:
chunks.append(tagNumber & 0x7f)
tagNumber = tagNumber >> 7
bLen = 1
for i in reversed(chunks):
outBuf[bOffset+bLen] = 0x80
outBuf[bOffset+bLen] += i
bLen += 1
#clear the high bit on the last part
outBuf[bOffset+bLen-1] &= 0x7f
return bLen

@staticmethod
def _toBytesStatic(tagClass, isConstructed, tagNumber, outArray, bOff):
tag = {True: ConstructedBERTag,
False: PrimitiveBERTag}[isConstructed]()
tag.init(tagClass, tagNumber)
return tag.toBytes(outArray, bOff)

toBytes = toBytes()

class PrimitiveBERTag(BERTag):
def __init__(self):
BERTag.__init__(self)
self._PC = 0 # primitive

def init(self, param1, param2):
self._tagClass = None
self._tagNumber = None
if isinstance(param1, list):
if (param1[param2] & 0x20) == 0x20:
# constructed tag
raise TLVException(TLVException.MALFORMED_TAG)
BERTag.init(self, param1, param2)
else:
tagClass = param1
tagNumber = param2
self._tagClass = tagClass
self._tagNumber = tagNumber

class ConstructedBERTag(BERTag):
def __init__(self):
BERTag.__init__(self)
self._PC = 1 # constructed

def init(self, param1, param2):
self._tagClass = None
self._tagNumber = None
if isinstance(param1, list):
if (param1[param2] & 0x20) == 0:
# primitive tag
raise TLVException(TLVException.MALFORMED_TAG)
BERTag.init(self, param1, param2)
else:
self._tagClass = param1
self._tagNumber = param2

15 changes: 15 additions & 0 deletions test/testTLVTag.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import unittest

from pythoncardx.framework.tlv import BERTag, PrimitiveBERTag, ConstructedBERTag

class BERTagTest(unittest.TestCase):

def testtoBytes(self):
array = [0 for i in xrange(10)]
self.assertEquals(1, BERTag.toBytes(1, False, 5, array, 0))
self.assertEquals(0x45, array[0])

self.assertEquals(3, BERTag.toBytes(1, False, 0x3fff, array, 0))
self.assertEquals(0x5f, array[0])
self.assertEquals(0xff, array[1])
self.assertEquals(0x7f, array[2])

0 comments on commit 4c500d3

Please sign in to comment.