Encryption

49 views
Skip to first unread message

Russell Wheeler

unread,
Nov 6, 2018, 6:19:41 AM11/6/18
to kryonet-users
I'm not that sharp when it comes to networking and encryption, so my questions may seem dumb/obvious, but I'll try anyway.

I see that through the means of custom serializers we can attempt things like encryption.

Now I'm not happy with the blowfish one because that's symmetric so if i understand correctly,i have to keep the password stored in the app which isn't secure.

Could i roll my own to do async encryption, i.e. to use a public key in the app to encrypt stuff and a private key on the server to decrypt it?

Philip Whitehouse

unread,
Nov 6, 2018, 7:21:31 AM11/6/18
to kryone...@googlegroups.com
That’s not the best approach.

What you want is to use public-private encryption to exchange the key used for subsequent symmetric encryption.

The reason is that public-private key encryption is slow whereas symmetric is not.

This is the approach SSL/TLS takes.

I would have thought there’d be a SSL/TLS filter - if not it’s a worthwhile project and worth getting community involvement to ensure that you’re not introducing any holes.

Regards,

Philip Whitehouse
> --
> You received this message because you are subscribed to the "kryonet-users" group.
> http://groups.google.com/group/kryonet-users
> ---
> You received this message because you are subscribed to the Google Groups "kryonet-users" group.
> To unsubscribe from this group and stop receiving emails from it, send an email to kryonet-user...@googlegroups.com.
> For more options, visit https://groups.google.com/d/optout.

Russell Wheeler

unread,
Nov 6, 2018, 7:32:44 AM11/6/18
to kryonet-users
Thanks for a quick response.

So how slow are we talking? Using kryonet I'm only sending strings that are less than a few hundred characters long. Surely that would be encrypted almost instantly?

I also don't get how the client and server could exchange a symmetric key without first exchanging a public/private key that is generated by the client.

In which case, I've already made those, why then use a symmetric one (apart from like you said for performance).

I've also thought about not using kryonet at all, and using SSL/TLS but I can't seem to find a way of doing that without using http and i don't really want to use that, because I'd have to buy a domain, and have to use a webserver on the other end to direct the traffic to the correct part of my code.

I'm really loving how simple kryonet is with it talking directly to the server.

Joachim Durchholz

unread,
Nov 6, 2018, 2:20:29 PM11/6/18
to kryone...@googlegroups.com
Am 06.11.18 um 13:32 schrieb Russell Wheeler:
> So how slow are we talking? Using kryonet I'm only sending strings that
> are less than a few hundred characters long. Surely that would be
> encrypted almost instantly?

Encrypting short strings comes with its own, very special challenges.
For example, an attacker might infer information merely by observing
packet size. The shorter the strings, the more interesting packet sizes
can be - unless you know that all packets are of the same size. (That's
why many crypto protocols use padding to multiples of a given block
size. Which may become useless if a compression algorithm is introduced
at the wrong stage which eliminates the padding again...)

> I also don't get how the client and server could exchange a symmetric
> key without first exchanging a public/private key that is generated by
> the client.

It could be the client, the server, or both who're generating key pairs.
But other than that: Yes, that's what's done; these keys are in
principle enough to do all further encryption.
However, asymmetric crypto is slow, so most protocols use it to transmit
a randomly-generated symmetric key and use AES or something similarly
fast. The downside is that this considerably complicates the protocol,
and if the symmetric key leaks, then all communication can be decrypted
post-hoc, so protocols have started further complicating things by
regularly scheduling a regular key update - and bugs in the
implementation of these methods have, time and again, led to nasty
protocol attacks (e.g. a malicious attacker can intercept the data
stream and force a key renegotiation sequence, and the bugs allow the
attacker to slip in his own symmetric key, or extract one bit of secret
key information, or something else).

In other words: Don't do this at home.

What makes this all really hard is that you cannot test your security.
Your protocol will work, hopefully, but that's all you see; you won't
see the glaring security holes.
Unless you're a real security expert, but you say you aren't. And even
security experts tend to overlook holes in their own crypto work, that's
why the security community places a huge weight on peer review of
everything: Concepts, protocols, implementations.

> I've also thought about not using kryonet at all, and using SSL/TLS but
> I can't seem to find a way of doing that without using http and i don't
> really want to use that, because I'd have to buy a domain, and have to
> use a webserver on the other end to direct the traffic to the correct
> part of my code.

You do not need to buy a public domain name for SSL/TLS etc.
If the recipes you've been reading assume that, then they're too
high-level and not useful for you (and most likely not in-depth enough
to be of sufficient quality anyway).

HTH.

Regards,
Jo

P.S.: I have given up on trying anything special with crypto. I just use
HTTPS, with a standard domain name, and if I need a public DNS name I
choke up that handful of dollars per month; but usually I'm coding in a
corporate environment where the domain names are set up anyway.
Still, a domain name isn't really necessary, and I'd disbelieve anybody
who told me otherwise.

Russell Wheeler

unread,
Nov 6, 2018, 7:26:58 PM11/6/18
to kryonet-users
Hey, thanks for chipping in, some very useful info there.

First, let me discuss the SSL/TLS stuff. If you have a few mins, and are better at Googling than me, I'd love to see something that doesn't involve https.

At the very least, I see that you need to have a certificate backed by a trusted keystore, like verisign or letsencrypt. I think verisign costs money and lets encrypt only let you use domain names not IP addresses, and domain names are more money :(

Then I'm not sure how I can even talk to my server app. If it's via http calls, and I do it in Java, I need apache/nginx to route the traffic then tomcat to again route the calls to the java lines of code. With Kryonet I need none of that stuff. That's why I love it so much!

So, the AES symmetric thing scares me. Just because, like you said, if you use symmetric then the key might be compromised. 

So I think I'm going to be an idiot/pigheaded call it what you will and plough on with my original idea! Not that I'm not grateful, but mainly because I'm kinda intrigued to go it my own way (because I feel very clever/arrogant for coming up with my own way and I want to see it through) and also because I've got the kryonet talking back and forth part all done, all be it without the all important encryption part. To tear all that down and to try and read a load more tutorials on SSL/TLS etc, feels like a lot of work (and I'm nothing if not lazy!)

So my end solution is to write my own Serializer for Kryo, one that takes a key pair. In the read method, I will use the private key to decrypt and in the write method I will use the public to encrypt.

My app is probably so small that no-one would even think of hacking it, so fingers crossed this is enough anyway. Hell, I could probably not encrypt any of it, but I feel passing/storing passwords etc in plaintext is wrong even on my little app.

Thanks for all your help, and feel free to tear into my latest hair brained idea! I've got no-one else to keep me from doing stupid things!

Russ

Joachim Durchholz

unread,
Nov 7, 2018, 2:45:08 AM11/7/18
to kryone...@googlegroups.com
Am 07.11.18 um 01:26 schrieb Russell Wheeler:
> Hey, thanks for chipping in, some very useful info there.
>
> First, let me discuss the SSL/TLS stuff. If you have a few mins, and are
> better at Googling than me, I'd love to see something that doesn't
> involve https.
>
> At the very least, I see that you need to have a certificate backed by a
> trusted keystore, like verisign or letsencrypt.

That depends. If you control both ends of the exchange, you can tell
them to trust whatever root certificate you want. Essentially you build
a root certificate, add it to the Java truststore on both sides, and all
is fine.
There's a lot of detail involved, and you'll have to fiddle a lot to get
it right - and I can't provide all of them because I just work with a
similar infrastructures set up by others, I don't do the nitty-gritty
details.

I don't know about that domain name vs. ip address difference. I have
never used IP addresses.
OTOH if you code you probably can tell the SSL library what domain name
each side is going to fake.
OT3H IP address isn't as unique as you likely assume. Machines have
multiple IPs: One for ethernet, one for Wifi, and possibly one for the
unused chipset Wifi; if you have Virtualbox, at least(!) one for the
virtual network interface. Even when filtering out the obviously
uninteresting IP addresses, my at-work laptop had three publicly visible
IP addresses. Well, not public but external - behind a NAT firewall, the
IP address is lost anyway.

Unless you have full control over IP addresses, it's best to stick with
some other naming scheme. If you code both client and server, I'd expect
that you can choose whatever you want for both sides, possibly even the
user name.

The trusted root certificate is important if you want to run a website
that is considered trustworthy by all browsers, no more. And no less, of
course - being accepted by all browsers gives you a vast potential
audience, that's why everybody and their teapot wants one.


> I think verisign costs
> money and lets encrypt only let you use domain names not IP addresses,
> and domain names are more money :(

Domain names are cheap.
Single-digit cost per month, and if you go even cheaper, it might even
go below one dollar.
You're paying more money for the electricity.

> Then I'm not sure how I can even talk to my server app. If it's via http
> calls, and I do it in Java, I need apache/nginx to route the traffic
> then tomcat to again route the calls to the java lines of code.

You really need to learn a lot.

Apache is a web server. It routes incoming calls to directories, or to
plugins that know how to generate a webpage, most prominent those that
start a "web language" interpreter and run some Perl, PHP, Ruby, or
whatever code.
You need none of that. You can use Tomcat as a full replacement,
provided you're willing to let all URLs go through your code.
For development, use Jetty to test stuff (Jetty is unrelated to Tomcat,
but it does as much as is needed for development).
Also, give Spring Boot a try. It comes with Jetty embedded, and if it
finds it started outside of Tomcat it will automatically fire up Jetty.
Or some other web servicing framework if you reconfigure it, but you
don't want or need to do that at your current expertise, you'll be
pretty intense about getting your HTTP connections to run.

You can do Kryonet, but if you want encryption, stick with HTTPS; you'd
have to do a lot on your own, and you need to get experience with
networking basics before delving into the details of crypto.

> So I think I'm going to be an idiot/pigheaded call it what you will and
> plough on with my original idea! Not that I'm not grateful, but mainly
> because I'm kinda intrigued to go it my own way (because I feel very
> clever/arrogant for coming up with my own way and I want to see it
> through)

Don't. Or do it, but don't plan to ever use it in production.
Even experienced engineers usually fail miserably if they roll their own
crypto.
The basic problem here is that you never find out if you failed in your
testing phase. You don't even find out in production. You find out when
you are in production AND your user base is so large that you have
become an interesting target - and at that point, you're stuck with your
code, you'd need to rewrite everything (because adding security as an
afterthought is an exercize in whack-a-mole and will eat your developer
time like nothing, without you getting anywhere really useful).

> and also because I've got the kryonet talking back and forth
> part all done, all be it without the all important encryption part. To
> tear all that down and to try and read a load more tutorials on SSL/TLS
> etc, feels like a lot of work (and I'm nothing if not lazy!)

Then doing your own crypto is even less of an option.

If you're lazy, go by the Spring Boot route.
Use HTTPS as a transport.
KryoNet isn't for getting a secure connection, it's geared towards
small, specialized use cases where you control the network.

> My app is probably so small that no-one would even think of hacking it,
> so fingers crossed this is enough anyway. Hell, I could probably not
> encrypt any of it, but I feel passing/storing passwords etc in plaintext
> is wrong even on my little app.

Actually that's a relatively useful option: publish the public key in
the app and keep the private key in the server.
The network will be 100% compromised if somebody hacks the server (and
somebody will). You should warn your users that they should not use your
app if they are under threat from state-level agencies (secret services,
police, or the mafia) because, because these are going to break into the
server if they want to (they won't break the crypto but simply hack the
server, or possibly subpoena you, or make "an offer you can't deny").

> Thanks for all your help, and feel free to tear into my latest hair
> brained idea! I've got no-one else to keep me from doing stupid things!

:-)

Oh, it's "hare-brained" BTW, but "hair-brained" will work ;-P

Regards,
Jo
Reply all
Reply to author
Forward
0 new messages