Access the classes JAR file as a ZIP?

K

kadingserver

Hello,

Is it possible to programatically get information about the JAR file
from which an application is being run?

I'm loading an application through Java Web Start and I'd like to be
able to determine:
1. the size of the JARS included with the application
2. the date they were packaged

Can I somehow access these JAR files as ordinary java.io.File (or
rather java.util.zip.ZipFile)? With a normal application I would think
it wouldn't be too hard. But I'm not sure how to locate the file when
they have been loaded in Java Web Start. I suppose it'd be necessary
to look into the JWS cache or something?

Thanks in advance,

KAding
 
A

Andrew Thompson

Is it possible to programatically get information about the JAR file
from which an application is being run?

I'm loading an application through Java Web Start and I'd like to be
able to determine:
1. the size of the JARS included with the application

<zen question>
Is that before they arrive, or after being cached? + *
2. the date they were packaged

* Why? What does this information offer the end user?
Can I somehow access these JAR files as ordinary java.io.File (or
rather java.util.zip.ZipFile)? With a normal application I would think
it wouldn't be too hard. But I'm not sure how to locate the file when
they have been loaded in Java Web Start. I suppose it'd be necessary
to look into the JWS cache or something?

It's better off looking into the reasons why you think
this strategy is required.

--
Andrew Thompson
http://www.athompson.info/andrew/

Message posted via JavaKB.com
http://www.javakb.com/Uwe/Forums.aspx/java-general/200710/1
 
K

kadingserver

(e-mail address removed) wrote:

..



<zen question>
Is that before they arrive, or after being cached? + *


* Why? What does this information offer the end user?




It's better off looking into the reasons why you think
this strategy is required.

Thank you for your reply.

Those are reasonable questions. So let me explain what I am trying to
do.

I have made a multiplayer game that is being deployed using Java Web
Start. Like many games we run into occasional problems with cheaters
who use speed-cheats, fake packets or in extreme cases even decompress
and decompile the jars included in the game to achieve unfair
advantages through some small changes. I can deal with the first two
in several ways and have already done so.

But I'm still looking into ways to make simple decompression +
decompilation less useful for cheating. I already obfuscate my JAR and
that is certainly helpful! However, I'm trying to develop a way for
the game server to verify whether a client is using a different
version of the game code or resource JARS. I know this can never be
foolproof. I know this will never stop a determined and skilled
cheater. Yet, the majority of those attempting to cheat are neither
particularly skilled, nor determined. So I'm just looking for ways to
put up some minor obstacles.

One of those things I was thinking of was too simply check the date
and size of the JAR. If they do not match, I can assume there has been
some tampering going on. Again, I know this will not be foolproof.
They can alter the decompiled code to fool there server, but this will
still serve as a decent obstacle, especially since the code is
obfuscated. So thats why I was wondering about accessing the JARS on
the classpath.

But by all means, if anyone has any suggestions on how to detect
whether a JAR has been tampered with I'd gladly hear it. Again, I'm
not looking for completely security, I just want to put up some minor
barriers. So to answer your question: "What does this information
offer the end user?". I hope it will offer them a more enjoyable game!

Thanks :)
 
P

Patricia Shanahan

But by all means, if anyone has any suggestions on how to detect
whether a JAR has been tampered with I'd gladly hear it. Again, I'm
not looking for completely security, I just want to put up some minor
barriers. So to answer your question: "What does this information
offer the end user?". I hope it will offer them a more enjoyable game!
....

How about using the ClassLoader's getResourceAsStream method to examine
some of the critical resources? You could either look for value-offset
pairs, or sumcheck the whole stream.

To make it a bit more difficult to find and remove, keep several
(resource,sumcheck) pairs, and make random choices of which to test when.

A cheater might preserve file sizes and modified dates, but must change
the value of a resource when your code accesses it in order to have any
effect.

Patricia
 
R

Roedy Green

I'm trying to develop a way for
the game server to verify whether a client is using a different
version of the game code or resource JARS. I know this can never be
foolproof
All he need do in provide an unmodified jar for your code to look at.

Here are some tactics I might try to deter such tampering.

1. every X seconds you download a new class. You keep the app
constantly shifting so you don't give him a moving target.

2. You do some of the computation purely on the server. He then has
to expose his experiments to you.

3. hide in your code tampering checks that you DON'T invoke right
away.

4. Lard your code with red herrings, code and variables that LOOK like
they are valid, but just so somewhat insane things. You waste his
time tracking them down.

5. Your code that detects tampering should not trigger its alarm right
way, but bide its time. This helps frustrate the hacker by making him
think he has solved the problem, when he hasn't really. He never know
how many more delayed time bombs you have set for him.

6. read http://mindprod.com/jgloss/obfuscator.html

7. Implement your code in several different ways. Keep randomly
combining different pieces which code that checks that the other
pieces are as expected, perhaps by a sanity timing check, not
something direct like a checksum.
 
J

Joshua Cranmer

They can alter the decompiled code to fool there server, but this will
still serve as a decent obstacle, especially since the code is
obfuscated. So thats why I was wondering about accessing the JARS on
the classpath.

Then make the code undecompilable (requires post-compilation checks).
Recommendations:

1. Add an invokedynamic instruction and watch the decompilers melt as
they meet an instruction that can't be reproduced using Java.
2. Change an <init> constructor to call the super after doing some
modifications. Valid in JVM spec, not valid in JLS.
3. Separate out the new instruction from the superclass invocation. In
some cases, this won't even violate the JLS but will still cause
meltdowns in decompilers.
4. (The most tortuous, IMO) Write some code where the difference between
fcmpl and fcmpg actually becomes important, flip those in the bytecode,
and then watch as the decompiled output probably doesn't match the exact
functionality of the bytecode. (The instructions differ on what they do
if they meet a NaN) Bonus points for making this functionality
non-intuitive.
 
K

kadingserver

Wow, these are all great suggestions! I'll see if I can implement them
right away! :)

Thanks a lot!
 
A

Andrew Thompson

Wow, these are all great suggestions!

I agree. I am glad that you added the extra details of
the 'end goal'.

This is not an 'end' to which I am greatly inclined to help,
but I was impressed by the cleverness of the answers of
the other responders.
...I'll see if I can implement them right away! :)

I'm sure there are a number of people who would be
interested to hear your progress.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,755
Messages
2,569,535
Members
45,007
Latest member
obedient dusk

Latest Threads

Top