Skip to content

Commit 853fea2

Browse files
author
vbuell
committed
Native types in arrays now supported
1 parent d7c2d57 commit 853fea2

File tree

1 file changed

+71
-43
lines changed

1 file changed

+71
-43
lines changed

javaobj.py

Lines changed: 71 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ def loads(object):
55
"""
66
Deserializes Java primitive data and objects serialized by ObjectOutputStream
77
from a string.
8+
See: http://download.oracle.com/javase/6/docs/platform/serialization/spec/protocol.html
89
"""
910
f = StringIO.StringIO(object)
1011
marshaller = JavaObjectMarshaller()
@@ -162,30 +163,17 @@ def do_classdesc(self, parent=None, ident=0):
162163
(type, ) = self._readStruct(">B")
163164
field_name = self._readString()
164165
field_type = None
165-
if type == 0x44: # 'D': Double
166-
field_type = "double"
167-
elif type == 0x49: # 'I': Integer
168-
field_type = "integer"
169-
elif type == 0x4A: # 'J': Long
170-
field_type = "long"
171-
elif type == 0x53: # 'S': Short
172-
field_type = "short"
173-
elif type == 0x5A: # 'Z': Boolean
174-
field_type = "boolean"
175-
elif type == 0x5B: # '[': Array
166+
field_type = self.convert_char_to_type(type)
167+
168+
if field_type == "array":
176169
field_type = self.read_and_exec_opcode(ident=ident+1, expect=[self.TC_STRING, self.TC_REFERENCE])
177170
if field_type is not None:
178171
field_type = "array of " + field_type
179172
else:
180173
field_type = "array of None"
181-
elif type == 0x42: # 'B': Byte
182-
field_type = "byte"
183-
elif type == 0x46: # 'F': Float
184-
field_type = "float"
185-
elif type == 0x4C: # 'L': Object
174+
elif field_type == "object":
186175
field_type = self.read_and_exec_opcode(ident=ident+1, expect=[self.TC_STRING, self.TC_REFERENCE])
187-
else:
188-
raise NotImplementedError("type 0x%X isn't implemented yet" % type)
176+
189177
self.print_ident("FieldName: 0x%X" % type + " " + str(field_name) + " " + str(field_type), ident)
190178
clazz.fields_names.append(field_name)
191179
clazz.fields_types.append(field_type)
@@ -259,31 +247,10 @@ def do_object(self, parent=None, ident=0):
259247
print "Prepared list of types:", megatypes
260248

261249
for field_name, field_type in zip(megalist, megatypes):
262-
if field_type == "boolean":
263-
(val, ) = self._readStruct(">B")
264-
res = bool(val)
265-
elif field_type == "byte":
266-
(res, ) = self._readStruct(">b")
267-
elif field_type == "short":
268-
(res, ) = self._readStruct(">h")
269-
elif field_type == "integer":
270-
(res, ) = self._readStruct(">i")
271-
elif field_type == "long":
272-
(res, ) = self._readStruct(">q")
273-
elif field_type == "float":
274-
(res, ) = self._readStruct(">f")
275-
elif field_type == "double":
276-
(res, ) = self._readStruct(">d")
277-
else:
278-
res = self.read_and_exec_opcode(ident=ident+1)
250+
res = self.read_native(field_type, ident)
279251
java_object.__setattr__(field_name, res)
280252
return java_object
281253

282-
# field_type = "double"
283-
# field_type = "long"
284-
# field_type = "array of " + field_type
285-
286-
287254
def do_string(self, parent=None, ident=0):
288255
self.print_ident("[string]", ident)
289256
ba = self._readString()
@@ -295,9 +262,25 @@ def do_array(self, parent=None, ident=0):
295262
classdesc = self.read_and_exec_opcode(ident=ident+1, expect=[self.TC_CLASSDESC, self.TC_PROXYCLASSDESC, self.TC_NULL])
296263
(size, ) = self._readStruct(">i")
297264
self.print_ident("size: " + str(size), ident)
298-
for i in range(size):
299-
res = self.read_and_exec_opcode(ident=ident+1)
300-
print res
265+
266+
array = []
267+
268+
# for char in classdesc.name:
269+
typestr = self.convert_char_to_type(classdesc.name[0])
270+
assert typestr == "array"
271+
typestr = self.convert_char_to_type(classdesc.name[1])
272+
273+
if typestr == "object" or typestr == "array":
274+
for i in range(size):
275+
res = self.read_and_exec_opcode(ident=ident+1)
276+
print res
277+
array.append(res)
278+
else:
279+
for i in range(size):
280+
res = self.read_native(typestr, ident)
281+
print "Native value:", res
282+
array.append(res)
283+
# raise RuntimeError("Native types aren't supported in arrays")
301284

302285
return None
303286

@@ -326,6 +309,51 @@ def hexdump(self, src, length=16):
326309
result.append("%04X %-*s %s\n" % (i, length*3, hexa, printable))
327310
return ''.join(result)
328311

312+
def read_native(self, field_type, ident):
313+
if field_type == "boolean":
314+
(val, ) = self._readStruct(">B")
315+
res = bool(val)
316+
elif field_type == "byte":
317+
(res, ) = self._readStruct(">b")
318+
elif field_type == "short":
319+
(res, ) = self._readStruct(">h")
320+
elif field_type == "integer":
321+
(res, ) = self._readStruct(">i")
322+
elif field_type == "long":
323+
(res, ) = self._readStruct(">q")
324+
elif field_type == "float":
325+
(res, ) = self._readStruct(">f")
326+
elif field_type == "double":
327+
(res, ) = self._readStruct(">d")
328+
else:
329+
res = self.read_and_exec_opcode(ident=ident+1)
330+
return res
331+
332+
def convert_char_to_type(self, type_char):
333+
if type(type_char) is str:
334+
type_char = ord(type_char)
335+
336+
if type_char == 0x44: # 'D': Double
337+
return "double"
338+
elif type_char == 0x49: # 'I': Integer
339+
return "integer"
340+
elif type_char == 0x4A: # 'J': Long
341+
return "long"
342+
elif type_char == 0x53: # 'S': Short
343+
return "short"
344+
elif type_char == 0x5A: # 'Z': Boolean
345+
return "boolean"
346+
elif type_char == 0x5B: # '[': Array
347+
return "array"
348+
elif type_char == 0x42: # 'B': Byte
349+
return "byte"
350+
elif type_char == 0x46: # 'F': Float
351+
return "float"
352+
elif type_char == 0x4C: # 'L': Object
353+
return "object"
354+
else:
355+
raise NotImplementedError("type 0x%X (%s) isn't implemented yet" % (0, type_char))
356+
329357
# =====================================================================================
330358

331359
def dump(self, obj):

0 commit comments

Comments
 (0)