Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 1 year ago.
Improve this question
I would like to encrypt data that travels back and forth between the server and client in my Web application. I would use SSL but that requires a certificate along with a dedicated IP address. I have no problem getting a certificate but the dedicated IP requires me to upgrade to a business hosting plan which is $20 a month on my Web host. I have no plans on doing that as I'm sticking with my $20/year shared hosting plan.
So, I would like to implement an alternative to SSL. It does more than SSL does, though. Along with encrypting the data sent back and forth, it also encrypts the rows in the database. I was thinking of doing something like this:
JavaScript Code:
var transfer_key = 'whatever';
function encrypt(data, key) {...}
function decrypt(data, key) {...}
function send_data_to_server(url, data)
{
$.post(url, {'data' : encrypt(data, transfer_key) }, function(response) {
var decrypted_response = JSON.parse(decrypt(response));
});
}
PHP Code:
$data = $_POST['data'];
$transfer_key = 'whatever';
$storage_key = 'whatever2';
function encrypt($data, $key) {...}
function decrypt($data, $key) {...}
databaseQuery('INSERT INTO table VALUES (?)', encrypt($data, $storage_key));
$decrypted_data = decrypt($data, $transfer_key);
$response = processData($decrypted_data);
echo encrypt($transfer_key, $response);
As you can see, the data the client sends to the server is encrypted, and vice versa. And the data in the database is encrypted as well. Now of course, I would never implement the keys like that. I would probably have a second or third key that's randomly generated for each user. So transfer_key could be equal to a constant_key concatenated with a random key, and same goes for storage_key.
Would this be a good alternative to SSL?
How can I implement this type of encryption in such a way that it is harder to defeat? Are there any particular weaknesses to this approach?
I'm probably going to find a JavaScript library that takes care of the encryption and use PHP's mcrypt extension for the server-side. I was thinking of Blowfish, maybe AES256, but I'm not sure which one gives me the best ratio of encryption strength to memory consumption.
Advice?
Uh, oh. Good luck with that. Have you had a look at the TLS specification? Do you think you can come up with something adequate that will be tested by millions of people?
No, really, TLS has been tested and improved over the years by so many people, cryptographers who do nothing else than breaking such protocols, it would be a hard task coming up with something adequate.
SSL has been developed by experts in the field and they most certainly thought at first, too, that their protocol was absolutely unbreakable. But then there was version 2, then 3, then TLS v.1, v1.1 and now 1.2.
If you don't have any prior experience in designing secure protocols you should stick with the mainstream and use TLS/SSL.
Security is one of the rare fields where it makes sense and is actually cool to go with the mainstream, so I'd say the added money would be well spent.
Edit:
Maybe I was a bit harsh, and I lacked some explanation as to why your approach cannot compete with a somewhat complex protocol such as TLS, so let's analyze it:
How would you do the key exchange? For AES to work on both ends, you need to do a Key Exchange, for symmetric encryption, both parties need to possess the same key. As you said, you would like to generate it randomly on the client - so far so good. First problem - you need to generate a secure random number - otherwise, e.g. by using the built-in Javascript random number generator - attackers would be able to predict your random numbers after some time.
Let's say you got that mastered. Then the next problem arises, how would you send this key to the server in a secure manner, i.e. perform the key exchange? There you will need some form of authentication on the server side, otherwise just about anyone could impose as your server and do this:
trick people into sending their keys to their rogue server first
then forward the key to your server
your server would dutifully send the data encrypted with the established key
the attackers would intercept that data and happily read your secrets by decrypting with the key they just stole
So you need server authentication, at least, if not client authentication, too. This will imply that you need some form of asymmetric/public key cryptography to encrypt/wrap the key with the server's public key so that just the server is able to decrypt it.
Once you mastered that, you are still susceptible to more involved forms of attacks such as replay attacks, man-in-the-middle-attacks, reflection attacks, ...
Maybe you also want Perfect Forward Secrecy so that once a key does get compromised the attacker would not be capable of decrypting any past data. You will need Diffie-Hellman (preferably in its Elliptic Curve Cryptography form) to achieve this.
Last but not least, a session mechanism would probably also be nice so that you can pick up previous sessions with already established symmetric keys, so that you can reduce the load on the server by not having to re-establish it again using the somewhat resource-intensive public key algorithms.
-> Add a couple more features, such as securely negotiating an algorithm suite that both client and server acknowledge to support and you will have reimplemented the TLS protocol.
Sorry if this sounds a bit sarcastic, but I know it seems tempting to roll your own crypto schemes (it's fun, too), but in the end you should stick with TLS: it's (relatively) easy to use, it runs on the transport layer (so you can code your applications as if there were no encryption at all) and best of all, it's secure.
EDIT: Well, there have been some attacks recently, but almost all attacks exploited the "human factor" in these protocols by attacking the public key certificates that back the protocol (Comodo, DigiNotar etc. are prominent examples) or more arcane features of the protocol like algorithm negotiation etc., but the BEAST has been the first time that TLS has been successfully attacked on the cryptography level, which is interesting and scary at the same time, because the basics of that attack have been known for some years now.
Still, with recent fixes for BEAST in place by now, I would bet that TLS is still the best option you have for secure communication on the web, especially when compared to hand-crafted solutions.
Ryan: I'm saying this in what I hope is the best possible way: memory consumption is the absolute least of your problems.
There is nothing secure about this. Nothing. N.o.t.h.i.n.g.
It's dead from the very first sending of that javascript... I don't care how long your keys are or how random the salt is.
What you have won't stop someone sitting in a coffee shop with their laptop open grabbing packets from intercepting the keys and being able to easily decrypt everything else you pass back and forth. Heck, just seeing the words "encrypt", "decrypt", and "key" in the stream would be enough to pique someones interest to dive further for fun (or profit..). Never mind watching an open connection suddenly start transferring parts of the packets encrypted and other parts in the clear.
If what you have is worth encrypting then it's worth the additional $240/year to do it right. Please, step back from the ledge and just do it right.
Everyone is being so negative, and while I share the sentiment that you personally should probably not be doing this, let me make some general remarks:
For a secure channel you need three things:
line encryption
key exchange
authentication
For encryption, you need to implement a cipher. That's doable.
Key exchange is the crucial point: Both peers need to know that they know a common key without anyone else being able to know the common key. There exist protocols for that, and it should be possible to implement that. SSL is doing that, for example. The fact that you can sniff an SSL connection and not learn anything shows that it can be done.
Authentication is necessary to stop man-in-the-middle attacks, and this requires some sort of out-of-band information exchange (like a phone call or PKI infrastructure). Whether any of this really works practically is highly debatable, even for SSL.
So basically if you can implement all those components over HTTP, then in principle it should be possible to run secure communication over HTTP. After all, SSL is doing the same thing, it's running a secure channel over an insecure medium. Basically what you want is to implement SSL in JavaScript. Check out aSSL, they've tried something like that.
My advice is to stick with SSL/TLS. I think this will make your life easier and also give your solution industry recognized credibility.
Instead of the static IP address, could you use DynDNS (or similar service) with a self-signed certificate?
Related
This may be somewhat of a faugue description of my question, and I am unsure if this is best to be posted on Stackoverflow or on Super User.
My problem is the following, I am in planning stage of building an quiz ios-app. In some cases it would actually hand out physical prizes monthly, which means security must be tight enough to decrease cheating possibilities.
I will build a backend in PHP, on a debian server with Apache and a certified SSL (Rapid-SSL).
My guess is that for every question, it needs to send it back and forth to the server for the server to authenticate the answer, and let the user know if the answer was correct or not. For some cases (the non-price-winning quizzes) I even want to return the correct answer.
My question is, what is the best way of doing this, security wise? Should I encode the data that is being send back and forth, and if so... how and with what (is there some common encoding type which I can use, such as base64 or similar)?
Edit
What I meant was encoding, rather then encryption. I updated the question
Also, for authentication I was thinking of using Facebook OAuth login.
Let me explain this in detail:
a) If you are afraid of a man in the middle attack or modification of your packet before sending to server (or receiving data from server), SSL would stop them.
b) If you want to stop hackers/debuggers/reversers, if they reverse your code and your code submits for example high score in SSL, they can also submit it easily, like this:
https://yoursite.com/submithighscore.php?score=[SCORE]
even you are using https, when hacker revealed the URL, score submission method and HTTP parameters, they can also submit fake results using a simple curl command.
So in this case, you can implement an advanced encryption algorithm, like encrypting data using a known algortihm with some your application specific changes, secure your application from reversing (which is hard a little). It will stop most of hackers/reversers.
If you choose a good key-exchange algorithm and encryption schema, faking it for hackers would be hard, except injecting code or modifying your code. This time you have to take all anti-reversing measures. Even if you use a public-key encryption here without taking anti-reversing measures, hacker could inject a code in your application which will add for example X points to every submission of point, it will not take more than a single assembly instruction.
Anyway, it's hard to have a really really secure system, reversers gone reverse, code-breakers gone try to find out your encryption algorithm and try to break it. But you can also do your best to stop most of hackers.
If you are sending over SSL, the data definitely is already encrypted. Thinking about it, the biggest worry is authentication. Knowing for sure that the user that is submitting a question, is actually that user. For that, I would use simple password authentication. And because everything is over SSL, that should be enough. The biggest worry in that case is malware on the user end.
It's difficult to tell what is being asked here. This question is ambiguous, vague, incomplete, overly broad, or rhetorical and cannot be reasonably answered in its current form. For help clarifying this question so that it can be reopened, visit the help center.
Closed 10 years ago.
I know everyone uses TLS/SSL as transport layer security on the web.
What would prevent me from generating let's say keypair manually, encrypting data client-side (using JS for example) with that public key and submitting that data to my server with http's GET/POST request?
I mean - I can just use JS library to encrypt some form data with that public key - right?
Only person who has private key can decrypt it - right? And private key would be kept on the server of course. No key warning will pop up - since transmission is a regular http request. So why I need TLS?
How do you trust that the Javascript delivered to the browser is the Javascript that will encrypt with the correct key?
Think about it for a second, and realize that security best practices are very subtle and nuanced and simply slapping encryption on top is not a solution.
Also, if you're dealing with the "key popup", you've broken one leg of the TLS trust model (the trusted certificate authority) by using an unsigned server certificate.
Let's give an example of how this could go wrong. Let's say that what you're trying to encrypt is some form data and send it to the server. The server sends it's public key to the client to encrypt with. The client in JavaScript encrypts this data and sends it to the server. Assuming that's what happened you'd be okay.
Now let's explore how this could go wrong. With the status of switching and the like these days it is fairly hard to sniff someone else's packets without access to the hardware. Therefore, most of the cases you are trying to avoid also allow the attacker to present a man in the middle attack. In this case the attacker could provide the client with whatever JavaScript they pleased. A clandestine way of stealing data would be to provide JavaScript that does everything that the original JavaScript does, and the also sends the unencrypted data to another server.
This can happen in a similar fashion for data from the server being sent to the client.
P.S. If your problem is the lack of a CA signed cert, I would suggest getting a free one from http://www.startssl.com/
You are correct. You can do that, and you'll have utilized strong cryptography, which is in fact one of the underlying components of SSL/TLS.
One of the issues is that computing that for every piece of data is computationally expensive. You also need to have cross compatible libraries on the client and server that handle the encryption/decryption process.
However, you will have lost any transparency in your web application because you now have to perform this encryption process on every piece of data you need to keep secret.
TLS is session oriented, so this is not an apples to apples comparison. What TLS is doing is setting up an encrypted session that is transparent to the client and server. It's making an encrypted pipe and allowing data to flow through it. It also has baked in concepts of "Trust" and identity, so that a client can have some indication that the information they are sending is going to the person they think it is.
What you are describing is taking pieces of data, encrypting them, then sending the encrypted version, and requiring decryption on the other side prior to use. Your scheme can and will work if you want to go through the pain of getting it setup, but what have you gained? Furthermore, since your scheme will have none of the things that TLS has in preventing man in the middle attacks, it's susceptible to those problems in a number of ways -- from someone injecting their own library and key into the client so that your app starts sending data to them instead of you, or that they get between you and the client, and send data to you that your server believes is coming directly from them and is instead coming from the attacker.
Digital certificates include the public key of the subject, digitally signed by the CA using their private key. Your browser contains certificates identifying their public keys (signed, in the case of root certificates, with the same private key) and this allows your browser, assuming it trusts the pre-installed CA certificates, to verify your identity. When you access a server, the server-side certificate is used to transmit the server's public key to your browser, which it then uses to encrypt the initial exchange of credentials. When client-side certificates are required, similar considerations allow the server to identify you.
There's nothing to stop you using your public key in a JS library to encrypt data, but how is the server supposed to decrypt it? Passing it your private key negates the purpose of the private key, which is to ensure that only you can decrypt information encrypted with your public key. So the correct way to proceed would be to encrypt with your private key, but then anyone who has your pubic key can decrypt it (this technique is usually used for digital signature).
Really you should use the server's public key to encrypt your transmission, and let it use its private key to decrypt it. The whole business of secure key exchange is very subtle, and there are many examples (from IBM downwards) of companies and people developing their own encryption systems, relying on privacy of the algorithm. They have always proved to be relatively easy to break. Best not to design your own system until you have a little more security experience ...
Your question makes no sense.
If you generate a key pair and encrypt with the public key, only you can decrypt that message. So sending it to someone else is futile. You could encrypt with the server's public key, but then you have the problem of establishing exactly what that is, securely.
And then the server has no way to encrypt data back to you, unless it uses your public key, in which case it has the same problem of authenticating your identity that you already had as the client.
TLS/SSL solves those problems, and a few others you haven't thought of yet.
I have a application (made in Delphi) that contains a Authentication system (login & password).
This system is in PHP, and the application get results from PHP using HTTP GET method.
The system returns 'OK' if login and password are correct, and 'NO' if not correct.
Like this...
procedure Check;
var
x: string;
begin
x:=Get('www.mywebsite.com/auth.php?user=xxxxxx&pass=zzzzzz');
if x='OK' then
UnlockFeatures
else
MessageBox(0,'You're not VIP','Error',0);
end;
Well, it works fine, but it is very easy to circumvent this system with sniffers, packet editor or proxy.
So, I want to get some information (in PHP) that changes every time, and that could be possible get the same information by my application.
What can I do?
I don't need codes. Just tips, suggestions, please...
Thanks...
Generally i suggest you not to try to outsmart everyone and invent brand new bicycle - you'd 99% fail with some stupid error making your approach completely insecure. There were a lot of precedences like DVD encryption or Win95 security. You'd better try some industry-approved mechanics, that for years been tested for security, that should have readymade implementations for both Delphi and PHP. Few are
TLS (https:// protocol) http://en.wikipedia.org/wiki/Transport_Layer_Security - that would give no protection from MITM attacks, but it sounds exactly what you asked and would require least possible change.
You may try implementing SSO via integrated windows authentication if you server would support that
You may try setting up OpenID or OAuth environments. Generally their v.1 would be simpler than v.2
You may try to bail out of HTTP and use XMPP/Jabber authentication - they take security seriously and libraries for PHP and Delphi exist. Though it should not be much more secure than just using TLS, you may hope that dumb attackers would not be prepared for non-HTTP protocols (there is not internet outside Facebook and such).
You may use Bluetooth-like approach to make special connection("handshake") once (when both client and servers are controlled) just to make special "tokens" interchanged and stored. That is a generic trait to use "controlled environment" to make 1st connection and use some tokens to prove "we had met before" on later connections using generic challenge/response trait. Those tokens should be unique for each client-user-server combinations! If you'd make one server-global clients-shared set of tokens - they would just be easily copied form one client to another and no more security remains.
Those may be coefficients for some not most trivial RNG. constructed be server and saved by both client and server. Then server "challenges" with RNG seed and client should response with proper random value, prooving he knows coefficients.
Those may be some asymmetric crypto, where token is some random "message", then server sends client encruyption keys and expects the correct message encrypted by them, or the token is the password and server generates random text and expects it's correct crypto digital signature to be passed back. You may find encyption libraries at Torry.net for examples. Lockbox3 and Spring4Delphi are among most tested and noted crypto libraries for Delphi implementing some encrypting standards.
Consider you priorities and make your choice.
Would you be able to switch all the authentication layer in one key turn later, having absolutely no care for backward compatibility with non-updated clients, then you might choose the most simple one and only enhance it later if needed. If your users are lazy at upgrades then you'd better choose most secure approach from starters, since you would have no practical way to disable insecure implementation later.
I'm not familiar with Delphi (looooooong time ago...), but as far as the php and security is concerned:
I would use post instead of get (and https if possible)
If you can read php sessions with Delphi, you could add a session variable with a random number and add that as a hidden form field, send it in and check it against the session variable.
I'm trying to make a "normal" username/password login form secure, without needing HTTPS. My idea is this:
Server generates a keypair for some kind of assymetric encryption algorithm. It stores this keypair in a temporary table of sorts (or perhaps the local session data).
Server sends the form to the client and includes the public key.
User fills in the form.
Before it's sent to the server, Javascript encrypts the password using the given public key.
Form is sent.
Server decrypts the password with it's private key (which it gets from the temporary table, using the public key to find it).
What I need to know for this is:
Which encryption method is the best to use? RSA?
How can I decrypt the password in PHP?
And probably the most difficult one, how can I make Javascript encrypt the password?
In advance: I'm sorry for being negative, however;
Implementing your own security protocol is never a good idea, unless you're a highly trained security expert, or you actually don't really care about the security and only want to create an impression of security (marketing) and stop the script kiddies.
SSL is definitely not a fingerprint lock, as so say in your comments, JCryption and your proposal are equal to having a door where you can enter a two-digit code to open the door and you have infinite many retries. It's hard to break if you're not really interested and just passing by, but if you want to get in that house (and you probably do, else security wouldn't be needed), you will get in.
Another point is that people often forget to mention what they want to achieve. Security has the famous three components called CIA, namely confidentiality, integrity and availability. Is it for you important that the data you transport is confidential, or is integrity important (i.e. you're sure that the sent data comes from the one you expect and not the man in the middle)?
To make it concrete in this case, the only thing that you achieve here is that a passive attacker cannot see whats passing by on the line. As soon as your attacker gets active and changes the messages on their route, your whole security falls apart. So my advice would be to just stick with the solution the experts have come up with (TLS in this case, not ssl since that is the old version of it) and just make sure your server supports it.
edit:
Btw, SSL/TLS cannot work without certificates. The whole point in public key crypto is that there should be at least somewhere some trusted party.
On the other hand, if you don't care that your users will get an "invalid certificate" message, you can just create your own certificate which is really easy. In that case your certificate isn't trusted by the browsers, however, you can be sure that at least your communication is safe (okay, there are exceptions in this case, but still ...)
The argument that certificates should be for free is really from a perspective point of view. I think people who claim it is bogus/idiotic don't know what it takes to be a certification authority. These companies invest millions in order to keep the communication secure, and sure they make nice money out of selling certificates, but hey its their job and they also deserve to make money, just like any others.
edit2: after comments
I indeed say that you have a secure communication. However, you miss the point that with self signed certificates you dont know to whom you talk securely. Imagine a dark room which is completely isolated from eavesdropping a conversation. Now imagine the difference between such a room with and without light. If the room has light, you can actually see to whom you're talking securely and only choose to talk to people you like to trust. Now imagine doing the same in a completely dark room. You can only hope that the guy you talk to inside this dark room is just an ally and not your adversary. However, you cannot know that, just hope that it's ok. And although your conversation itself is secure, nobody can listen in, you still dont have "full" security.
If I, being a crook, do a man-in-the-middle attack, I can create a self signed certificate without the user noticing. So the advantage of using TLS with self signed certificates is that you have at least the implementation of the protocol corrent (and even implementing this is far from easy). Moreover you can avoid the ugly warnings by advising your users to manually trust the certificate once. However, this is only possible if you have a relatively small group of returning visitors, for a public website this is not really a solution.
This doesn't seem that secure from the perspective of the client. Two (related) problems:
How does the client trust the server? How can it verify that the key the sever's presenting is the one that belongs to it?
It's possible to do man-in-the-middle attacks. A malicious proxy could strip out and store the public key before the client sees it, substituting its own, then decrypt the password when the client authenticates, store it, and re-encrypt and send the response on so the client doesn't realise something's up.
What's wrong with ordinary SSL? There has to be a consensus that it's secure, otherwise vendors and organisations would drop support for it overnight. By contrast, most attempts to invent a funky new way to do security "on the cheap" usually miss something fundamental.
It looks like a lot of what you want to do is supplied by the jquery plugin JCryption. It even assumes PHP as the backend, so a good fit for you.
Livejournal does something similar to what you want where:
Server generates a challenge string, inserts this into form. [1]
Client generates response by MD5 hashing the password, then MD5 hashing the previous hash with the challenge prepended [2].
Server gets response, checks challenge validity, then does same as step 2, comparing the result to the response.
This is a very good idea, and it's already been done. See jCryption.
jCryption looks interesting, I've not seen it before.
But I have to ask what is wrong with SSL?
Encryption code is notoriously hard to do right, and you can bet that the SSL implementations found in browsers and http servers are much more rigorously tested and reviewed than the jCryption stuff.
That said, jCryption looks neat if you absolutely need to avoid SSL, and you're not dealing with super-sensitive information.
By storing the passwords in encrypted method on the server the server can retrieve the passwords and verify checksum sent by client. Send a session password and ask client to make a hash of session password and the user inputted password, do the same on the server and compare the two hashes.
This will not secure users from MITM attacks - local admins, NSA, telecom, router hijacks, but it will keep the password safe in open wlan.
I am interested in having something that I encrypt using a public key on a LAMPhp server, decrypted using the appropriate private key on the web client (firefox at least, best if it is standard javascript)
Note that what I want to do is -not- merely to have an encrypted connection using SSL/https. Or even to use browser-based client certificates as a login/access control method. I know how to do both of those things. What I want to do is more like emailing with gpg keys. I want to be able to create a short message that I will encrypt with a users public key that -only they- can decrypt using their private key. What I am looking for is not the privacy achieved automatically by ssl, but the ability to allow only particular users to decrypt messages. I know I can easily do this with gpg or perhaps SMIME, and perhaps that is the best way, but I would prefer a web-based alternative.
Firefox etc have a certificate stores, and I know that the private keys held there are unlikely to be exportable into javascript for obvious security reasons, but I would assume there is some way to -use- the certificates from javascript calls to decrypt something..
The reason I would like to do this, is that I need a secure method to give a randomly generated password to a particluar administrator. I am trying to implement full database translucency and public key cryptography seems like an important part of that effort. But this is one use-case that I am having trouble addressing without this kind of ability.
So on the php side I would use the openssl encryption calls like so...
<?php
$browsers_public_key = get_it_from_the_browser_via_apache_maybe();
openssl_public_encrypt($data,$encrypted_ends_up_here,$browsers_public_key);
echo "<html><head>
<script type='javascript'>
function decrypt_textarea(){
??
}
</script>
</head>
<body><textarea id='decrypt_me'> $encrypted_ends_up_here </textarea>
<div id='where_the_plaintext_goes'> </div>
</body> </html>";
?>
Note that I have found via stackedoverflow many fine javascript encrypton libraries... but I actually want to use keys imported into Firefox as per MyOpenId.com or CaCert.org
Does anyone know if this is possible?
Thanks,
-FT
It's been a while since you asked this question, but if you or anyone else is looking for a potential solution to this problem or a similar one, they should check out the JavaScript Forge project:
http://github.com/digitalbazaar/forge/blob/master/README
This project has an SSL implementation in JavaScript that will allow you to include a client-side certificate when communicating with Apache. You can also manually do RSA decryption using the associated private key (which you have access to in JavaScript).
For instance, the JavaScript could get/post to the server and include its client-side certificate. Apache could read this certificate, use the public key to encrypt whatever data is appropriate, and then return that data to the client. The client could then use its private key (in JavaScript) and decrypt the information and do something with it. This extra encryption is probably not even be necessary, however, if your server can authenticate the client-side certificate as the appropriate recipient of the secret you're trying to pass.
The Forge project also has the APIs to build a system for importing/exporting keys and certificates to/from Firefox or other browsers (if this is still a requirement for some reason). A little help from openssl might be necessary to get the keys/certs in the correct format for import/export (pem => pkcs12), but an example of how some of this works can be found in a JavaScript-based demonstration of WebID. WebID is a client-side certificate-based authentication system:
WebID management demo: https://webid.digitalbazaar.com/manage/
WebID authentication demo: https://payswarm.com/webid-demo/
Note that the SSL certificates for the above sites are self-signed and will require temporary exceptions to be added to your browser to view them. The sites do not require you to enter any personal information, they are for demonstration purposes only. However, if you go to the first link, you can generate keys in-browser (it uses Forge JavaScript to do this) and then you can see the private key and certificate that were generated, in PEM format, in the list at the top of the page. The key and certificate are persisted via Flash local storage.
Nearly 100% (if not that) of the source for the WebID management site is viewable since it is mostly JavaScript. Also, the Forge project itself (see the github link) is opensource.
Now that I understand what you're saying, I can give you a firm answer :)
The best I can tell you is that you can't get decent encryption in the way you're looking to do it. Private key encryption (namely RSA) uses very, very, very large numbers to do encryption. Using small numbers is very simple to crack computationally (there are only so many prime numbers) and the numbers get big extraordinarily quickly. Basically, with RSA, you need to take large numbers and raise them to large exponents. JavaScript is able to support quite large numbers, but you'll hit a wall with performance. With a 512-bit key, encryption of a few kilobytes can take up to a few seconds, while decryption can take seconds to minutes to do. The reason JS is so slow is simply because it's not a compiled language. Sure, you could decrease the key size, but anything larger than a couple kilobytes and you've got a problem.
Also, RSA is inherently insecure in a web page because the private key is transmitted alongside the data to be decrypted (unless it was transferred earlier), which enables anyone that receives the page to decrypt the data.
I'm going to assume that you're looking to do this because you want to obfuscate some code from your user or a client, so I'm going to recommend that you check out XOR encryption. Granted, it's nowhere near as secure as RSA, but it uses principles that can be very secure if used properly. For instance, if you use a random key that's used only once and has the same length as your data/code (an one-time pad), your encryption is "uncrackable". Even better, XOR encryption is FAST. Here are some resources:
http://guymal.com/mycode/xor_js_encryption/
http://javascript.internet.com/passwords/xor-encryption4.html
Hope you have luck with what you're trying to do!
I am searching exactly the same thing you do and wanted to use php's openssl-functions, too.
I was happy to see that on the phpside everything was working great with private/public key (encrypt/decrypt) and now wanted to find a way to use privatekey on clientside as you do.
!!!
IF you will find anything please let me know by email:
pki (at) life.de
!!!
And for the performance aspect:
You would encrypt the big parts with symetric encryption and only the decryption key with the public key of the client to excahnge it. So you dont't need to enrypt many kb.
But it seems to be an dead end with firefox, but with IE and ActiveX it seems possible with
CAPICOM (I had not much read about it now).
hxxp://geekswithblogs.net/shahed/archive/2007/05/03/112232.aspx
But for JavaScript/PHP have a look at (and read all comments at FAQ and other pages,too!In future maybe bidirectional communication was mentioned):
hxxp://www.jcryption.org/
hxxp://www.zend.com//code/codex.php?ozid=1323&single=1
Pure Javascript Public/Privatekey encryption
hxxp://shop-js.sourceforge.net/crypto2.htm
A helful FireFox-Addon for PKI:
hxxps://addons.mozilla.org/en-US/firefox/addon/4471
hxxp://www.mozilla.org/projects/security/pki/nss/tools/index.html
PHP with OpenSSL on Serverside / .NET on CLientside
hxxp://www.csharpbydesign.com/2008/04/asymmetric-key-encryption-with.html
Javascript OpenPGP
hxxp://www.hanewin.net/encrypt/
PS: stupid mechanism prevents me posting links ...
You don't handle SSL in your PHP. SSL is handled by the web server automatically. If you're using Apache, here's a simple tutorial:
http://www.debian-administration.org/article/Setting_up_an_SSL_server_with_Apache2
The idea is that you write your code like normal, and when the user accesses your site using https, the server automatically encrypts the connection. On the client side, the browser is capable of using the private keys that it already has to automagically decrypt the connection and present the code to the user agent.
Hope this helps!