Win a copy of The Little Book of Impediments (e-book only) this week in the Agile and Other Processes forum!
  • Post Reply
  • Bookmark Topic Watch Topic
  • New Topic

class byte code bloat

 
Jacob Abrams
Greenhorn
Posts: 1
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
I have been working with J2ME for a little while on very restrictive devices and came across an interesting problem. I was working on a device that had a limit of 16kb per data object. I had a class that contained a byte array like so:
final class MyBigByteArray {
public static final byte [] DATA = { 1, 2, 3 /* continues on to contain about 2500 items */ }
}
Now one would think that an array of 2500 final bytes would consume about... 2500 bytes of space, plus some overhead. When I compile it however I get a nice .class file that consumes over 16kb! I've tried everything I can think of to hint to the compiler that it can align this data as bytes... I tried casting every item as a byte like so: (byte)1, (byte)2, etc... but no luck.
So why the massive waste of space, running an obfuscator like proguard has no effect either. What is taking up all that space? Is there anything that can be done about it that? My solution is to write the byte array out to a file and then read it in for now, but I'd prefer the simplicity of just using the data directly since I know it will never change.
Thanks!
 
Howard Kushner
author
Ranch Hand
Posts: 361
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Hi Jacob,
Right off-hand I'd be tempted to try two things:
  • Read the spec for the VM and figure out how it allocates space
  • Try packing the bytes into ints (4 bytes per int) and doing some bit twiddling (shifting and masking) to get at the individual values


  • Hope this helps.
     
    Jim Yingst
    Wanderer
    Sheriff
    Posts: 18671
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    This topic will probably fare better in our J2ME forum, so I'm moving it there now...
     
    Jim Yingst
    Wanderer
    Sheriff
    Posts: 18671
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    So if I understand correctly, the problem is not the size of the byte[] array in the JVM, but the size of the class file containing the data used to initialize the array? E.g. if you comment out the list of 2500 constants, you can just create a new byte[2500], and that fits in the JVM OK? That's because the JVM spec mandates that class files use a structure with 5 bytes for each integer literal. (Except long, which uses nine.) Obviously that's not very efficient here, but the assumtion was that no one in their right mind would put 2500 literals in a class file. I think using a separate file for the data is best, if you can manage that in whatever configuration you're using. Put the data file in the same directory as the class file, and use getClass().getResourceAsStream(fileName) to read it and initialize your array. Should result in some substantial savings.
    However I should note that I know very little about the J2ME world, so there may be a much better solution which others here are about to point out...
     
    Stefan Wagner
    Ranch Hand
    Posts: 1923
    Linux Postgres Database Scala
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    And if you store the bytes as String(Buffer)?
    Of course "\0x01\0x02..." isn't that good readable, but I guess to convert between String and Byte should be helpful.
    Is it that what you meant when writing: 'Read from file'?
     
    • Post Reply
    • Bookmark Topic Watch Topic
    • New Topic