Does the PCI standard make any tangible differentiation between having unencrypted versus encrypted credit information pass through my system?
The major advantage of the transparent redirect and similar implementations at other providers is that the data doesn't pass through my server at all. To me this always seemed like a bit of a loophole in PCI compliance. My server that serves up the form which, if hacked, could easily be modified to send credit card details to an attacker is out of scope because it doesn't technically, "accept, transmit or receive" as worded in the PCI docs. Does receiving the data in encrypted format still afford me use of the loophole or are the PCI requirements more stringent than when using transparent redirect?
The PCI DSS does differentiate between handling encrypted data and handling unencrypted data -- some requirements are only in scope if handling unencrypted data. It's important to note that Transparent Redirect doesn't remove the need for a merchant to become PCI compliant, it only reduces the scope of what's necessary to achieve compliance.
It's true that if your form is hacked it could be modified to send credit card details to an attacker. But that's also true even if you're redirecting the user to a third party page like Paypal to complete the payment. If hacked, somebody could change the Paypal button to redirect to a malicious page.
I would like to know what Nate Lawson thinks about this, as he wrote a really long post explaining why (his words¹) "client-side JS crypto is a bad idea"².
"I have only heard of one application of JS crypto that made sense, but it wasn’t from a security perspective. A web firm processes credit card numbers. For cost reasons, they wanted to avoid PCI audits of their webservers, but PCI required any server that handled plaintext credit card numbers to be audited. So, their webservers send a JS crypto app to the browser client to encrypt the credit card number with an RSA public key. The corresponding private key is accessible only to the backend database. So based on the wording of PCI, only the database server requires an audit."
For completeness, the next two paragraphs in Lawson's post:
"Of course, this is a ludicrous argument from a security perspective. The webserver is a critical part of the chain of trust in protecting the credit card numbers. There are many subtle ways to trojan RSA encryption code to disclose the plaintext. To detect trojans, the web firm has a client machine that repeatedly downloads and checksums the JS code from each webserver. But an attacker can serve the original JS to that machine while sending trojaned code to other users.
While I agree this is a clever way to avoid PCI audits, it does not increase actual security in any way. It is still subject to the above drawbacks of JS crypto."
What stops the site owner from just stealing your credit card number in the first place?
These schemes are not about protecting against malicious site owners, they are about protecting data that legitimate site owners collect from being intercepted by third parties.
Can't quite grok it on this post, but where they describe "end-to-end", how exactly are keys generated and distributed? Are key fingerprints verified out of channel? How are they not susceptible to MITM attacks? Which, admittedly may be difficult, but still possible. How is this any better than sending CC data from browser to server via SSL, which at least has a CA system (as shitty as the whole CA thing is)???
You generate (on Braintree's site), a RSA keypair and you use the public key and JS library they provide.
You call a JS method on the fields you want to encrypt like credit card number and CVV, and it encrypts it using the public key.
When an user submits a form, you send the encrypted values to your server, and then you pass them off to Braintree's API as you normally would.
Braintree then decrypts it on their end using the private key. If you set it up properly, you are never aware of the users credit card number, CVV, etc.
It prevents your servers (if it's setup properly) from ever knowing the credit card details. SSL only prevents somebody from seeing the data as its sent, your server will still know the plaintext details.
It doesn't fix the fact that if your JS or the forms itself are compromised, credit card details can be leaked, but the transparent redirect setup has the same issue anyway.
17 comments
[ 4.9 ms ] story [ 56.4 ms ] threadhttp://stackoverflow.com/questions/205468/how-to-encrypt-a-v...
I don't really need the answer now, but I bet my old boss would be interested in this development...
The major advantage of the transparent redirect and similar implementations at other providers is that the data doesn't pass through my server at all. To me this always seemed like a bit of a loophole in PCI compliance. My server that serves up the form which, if hacked, could easily be modified to send credit card details to an attacker is out of scope because it doesn't technically, "accept, transmit or receive" as worded in the PCI docs. Does receiving the data in encrypted format still afford me use of the loophole or are the PCI requirements more stringent than when using transparent redirect?
It's true that if your form is hacked it could be modified to send credit card details to an attacker. But that's also true even if you're redirecting the user to a third party page like Paypal to complete the payment. If hacked, somebody could change the Paypal button to redirect to a malicious page.
¹ http://rdist.root.org/2011/05/09/encrypted-google-docs-done-...
² http://rdist.root.org/2010/11/29/final-post-on-javascript-cr...
"I have only heard of one application of JS crypto that made sense, but it wasn’t from a security perspective. A web firm processes credit card numbers. For cost reasons, they wanted to avoid PCI audits of their webservers, but PCI required any server that handled plaintext credit card numbers to be audited. So, their webservers send a JS crypto app to the browser client to encrypt the credit card number with an RSA public key. The corresponding private key is accessible only to the backend database. So based on the wording of PCI, only the database server requires an audit."
"Of course, this is a ludicrous argument from a security perspective. The webserver is a critical part of the chain of trust in protecting the credit card numbers. There are many subtle ways to trojan RSA encryption code to disclose the plaintext. To detect trojans, the web firm has a client machine that repeatedly downloads and checksums the JS code from each webserver. But an attacker can serve the original JS to that machine while sending trojaned code to other users.
While I agree this is a clever way to avoid PCI audits, it does not increase actual security in any way. It is still subject to the above drawbacks of JS crypto."
These schemes are not about protecting against malicious site owners, they are about protecting data that legitimate site owners collect from being intercepted by third parties.
You generate (on Braintree's site), a RSA keypair and you use the public key and JS library they provide. You call a JS method on the fields you want to encrypt like credit card number and CVV, and it encrypts it using the public key. When an user submits a form, you send the encrypted values to your server, and then you pass them off to Braintree's API as you normally would.
Braintree then decrypts it on their end using the private key. If you set it up properly, you are never aware of the users credit card number, CVV, etc.
It prevents your servers (if it's setup properly) from ever knowing the credit card details. SSL only prevents somebody from seeing the data as its sent, your server will still know the plaintext details.
It doesn't fix the fact that if your JS or the forms itself are compromised, credit card details can be leaked, but the transparent redirect setup has the same issue anyway.