I'm looking for secure ways to pass data between a client running Flash and a server. The data in question will be generated BY the Flash app, which in this case is your score after finishing a game. I want to verify the data is untampered on the server. What are some good methods of getting this done?
One simple way is to perform some operations on the data such as a hash, and pass the hash back to the server along with the data. This is easily broken by someone with access to the client source code, however.
Edit: I realize that nothing will be unhackable, but I want to make it as difficult as possible. @jcnnghm's solution of encryping data with a public key and optionally doing sanity-checks and/or recalculation with the game logs is the best option I think. SSL encryption is also a good idea as this makes it more difficult to decipher what's actually being sent back to the server.
Encrypt the data with a public key stored in the binary. This will raise the barrier of entry for an attack. In addition to that, sanity check the data as it arrives on the server. This could be as simple as calculating the maximum number of points that could realistically be earned per time unit of play, or transmitting game logs back to the server to make sure the scoring is correct.
Nothing is going to be totally hack proof, no matter what you do, but this will stop all but the most determined.
Update: @mark: Flash supports SSL natively.
Can code running on top of an un-trustworthy platform retain its integrity? No, decades of broken copy-protection schemes lead me to postulate that this is impossible. The inverse, malicious code running in a trusted sandbox is feasible, but the best you can do with your problem is make it inconvenient for people to cheat.
Check out the AS3Crypto package at http://code.google.com/p/as3crypto/. I haven't tried it, but this package claims to (partially) support the TLS 1.0 protocol.
TLS will provide a secure tunnel between your Flash application and the server.
http://en.wikipedia.org/wiki/Secure_Sockets_Layer
@jcnnghm
You normally don't want to use public key encryption (RSA, DSA) for the bulk data encryption due to its' large computational time. Public key encryption should be used in the handshaking and key agreement phases in a security protocol, but the bulk data encryption should be handled by a symmetric cipher such as AES and TDES. The TLS and SSL protocols work this way.
As long as people can get at the executable - which, unless you want to run the game on a locked kiosk, is always the case - there's no perfectly secure way of doing this.
The music and movie industries spent tens of millions on DRM that got cracked by home hobbyists in days/weeks. If they can't protect their stuff...
I agree about the answers given about nothing is hacker proof. Because once you can read it, you can manipulate/copy it and therefor decompile it.
Another approach I have been planing is to generate unique keys pr. player session (including some kinda of time/date as salt values).
Then through out the application, perhaps periodically submitting/transmitting status score and gaining a new valid key. If this synkronisation fails, then break the whole session.
The downside on this could be too many simulitanious players bringing the reply speed of the server down and therefore making "fake timeouts" + leaving the gameserver open for DoS-attacks.
But something with renewing the "session key" while the user has the session, will requier at bit of extra session management, but if it will make the cheaters work a bit hardere I will sure try it :o)
On the other hand, NOTHING is hacker proof, so don't trust it 100% - no matter how clever a solution you think up.
A last note would also be to divide your application into modules/levels etc. so that you don't get access to every piece of the code, just by starting it.
Currently my plan is to build a large multilevel world and the client/player will ONLY get the files attached to the part the player resides in.
Hope this is of any use to your thoughts.