AddSigningCredential in IdentityServer4 - Self-signed or from a certificate authority - asp.net-core

I'm aware that a self-signed certificate is not a good idea to encrypt SSL traffic between a server and a browser. But does it matter in the context of IdentityServer4?
And where is the difference between that and AddValidationKey() which seems easier to me?
By all means, I'm not a security expert and unfortunately nobody in my team, so we are a bit confused here and I would like to avoid opening up a big security hole. At the same time, I don't want to complicate something that is not necessary.

First of all, when dealing with IdentityServer you have several keys/certificates to deal with.
You have the certificate for the SSL/TLS(HTTPS) traffic, and this one should not be self-signed.
You have AddValidationKey/AddSigningCredentials that both deals with the signing of the tokens. This needs a separate public/private key. This can be done using a self-signed certificate. See this article
You have also the Data Protection API to deal with, this is responsible for encrypting the session cookies issued. To avoid issues during redeploy, you should make sure the signing key (keyring) is persisted during redeploy.
Hope this is a starting point :-)

Related

Is my SSL certificate good enough for financial transactions on my shopping cart

I have an online shop and I've just installed a new SSL certificate and it was free. It does seem too good to be true. I'm a very cynical type of person.
I don't know about different types of SSL, but I just need to be able to accept payment data (I'm using a PayPal add-in on Opencart).
I got my certificate from letsencrypt and they don't explain much on there website.
But if you go to my website Gwenllian-retail you will see the certificate. Can I handle financial transactions with that?
If not what type of SSL do I need?
One does not need much money or complicated software to create valid SSL certificates. I could create my own with ease, if I wanted. In fact, I have done. There is no reason to think that LetsEncrypt certificates are somehow of a wrong kind.
The question is whether people will trust those certificates, and that comes back to whether they trust the Certificate Authority (CA) that signed them. If I sign my own certificate and present that to someone as proof of my identity then that other party has no more reason to trust that the data within accurately identify me than if I just told them directly.
LetsEncrypt serves as the CA for SSL certificates it provides. I have never relied on them for a certificate, but according to hosting company DreamHost, LetsEncrypt certificates are trusted by all major browsers. (LetsEncrypt makes the same claim about itself, too.)
Again, all this trust business is mostly about authentication: whether the entity that presents the certificate (your web site) is really the entity that it says it is. It is not about the nature or quality of the encryption with which the session is secured. That comes down to the capabilities of the two endpoints, and is largely independent of the certificate.
Let's Encrypt is a well known service backed up by many big players. So yes, it's OK to use it in on your site. BUT ! SSL certificate is not everything, it's only one of many shields to protect you application.

How to make sure Certificate is safe in WCF

WCF supports to use certificate to authenticate Client. If a malicious user steals client's certificate and creates connection with Server. Can Server know this? If we install certificate to Microsoft Certificate Store, how to make sure it is safe? I could easily read the certificate in store by code.
Can Server know this?
no.
If we install certificate to Microsoft Certificate Store, how to make sure it is safe?
you can't.
Certificates themselves don't solve secret leaking problem. They provide better security on a transport, better UX when authenticating on remote server, but they can leak as easy as passwords (ok, not that easy, but can). Such issues are solved using different techniques, like storing the certificate on a smart card where you need to have both, a card itself and PIN/Password to access the card. These are out-of-band solutions the certificate is not aware about, thus you can't tell whether the key is secure or not.

SSL Pinning and certificate expiry

This question relates to the use of SSL Pinning in a client app against a web api and certificate
expiry.
Scenario:
I own example.com and have a subdomain where an api is hosted, as such: api.example.com
I wish to use the api over SSL, so an SSL Certificate is created for the subdomain.
After the certificate has been acquired, I have:
A Public Certificate
A Intermediate Certificate
A Private Key
It's my understanding that I install these certificates on my webserver.
I then wish for my client app to connect to the api. To mitigate against man-in-the-middle style
attacks, I wish to use SSL Pinning, so that the client will only communicate with my api, not
someone spoofing it.
In order to pin in the client app, I have two choices, either pin against the public or intermediate
certificate.
Let's say I implement this.
What happens when the certificate on api.example.com expires?
It's my understanding that the client app would no longer work.
Do I need to regenerate a complete set of public/intermediate/private items again? and then
put a new public or intermediate certificate in the app?
Question:
I would still like the client app to work until the certificate on api.example.com was updated.
Of course, a new certificate can be put in the client app, but things like roll-out take time.
How can I handle this?
I've read that Google updates their certificate every month, but somehow manages to keep the public key the same: How to pin the Public key of a certificate on iOS
If that's possible, then the solution is to simply extract the public key from the server and check it against the locally stored public key...but how do Google do it?
Thanks
Chris
Note: I'm more familiar with browser to server pinning (HTTP Public Key Pinning - HPKP) rather than app to server pinning, but I presume the principal is the same. In HPKP the pinning policy is provided by the server as a HTTP header but understand this is often built into the app rather than read from the HTTP response. So read below answer with all that in mind:
Pinning is usually against the key not the cert and can be a multiple levels. So you've several choices:
Reuse the same key/crt to generate a new cert. Some (rightly in my opinion!) recommend generating a new key each time you renew your cert but this is complicated when you use pinning. So does pinning encourage poor security habits like key reuse?
Have several back up keys in your pinning policy and rotate them around on cert renewal discarding your oldest and adding a new one with plenty of time and updates to never be caught short. Personally I prefer to generate the key at cert renewal time rather than have some backups around which may or may have been compromised so I'm not a particular fan of this either. And how many backups should you have? E.g. If you need to reissue a cert because of compromise around renewal and also mess it up? So 2? 3? 100?
Pin further up. Say the first intermediate or the root CA cert. So any newly issued cert is still trusted (providing it's issued by same cert path) The downside of this is four fold: i) You still leave yourself open to miss-issued certs issued by that pinned cert (not a massive deal IMHO as you've still massively reduced your attack surface but still a concern to some people), ii) you cannot guarantee the client will use that intermediate cert as there are sometimes multiple valid paths. This second one is a much bigger deal. You'd think that providing the intermediate cert would guarantee this would be used but that's not the case (plenty of sha-1 examples of this). iii) There's no guarantee new cert will be issued by same intermediate or root (especially when technologies change like introduction of sha2), so to me this whole option is a non-starter iv) It ties you in to using same cert provider (perhaps not a big deal but I like the freedom to move). Not sure if apps support this feature natively anyway but browsers certainly do.
Renew in advance and do not use the new key until policy cache expires. For example if you have one year certs and a 30 day pinning policy then you can renew after 11 months, add the new key to the policy, then wait 30 days so you can be sure everyone will have picked up new policy or at least the old policy will have expired, then switch keys and certs. Depends on a short policy and potentially wastes a portion of that though (at least 30 days in this example), unless cert provider provides cert in advance starting on day after old policy expires. For an app, if pinning policy is hard coded into it, then this might involve the length of time it takes to push out an update.
Ultimately, because certs do require renewing, I'm not a big fan of pinning. I don't think making something that is subject to periodic renewal, semi-permanent is the right answer. And there are even some talk of pre-loading pinning policies in browsers which just makes me shudder.
Pinning provides assurance that a rogue CA is not issuing certs for your domain but how likely is that really compared to the hassle of pinning? Something like Certificate Transparency - or even report only pinning may be a better answer to that problem even if they don't actually stop that attack.
Finally locally installed roots (e.g. for antivirus scanners or corporate proxies), bypass pinning checks (on the browser at least) which again reduces its effectiveness in my eyes.
So think carefully before using pinning and make sure you understand all the consequences.
The mozilla developer site recommends to pin the certificate of the intermediate CA that signed the server certificate.
"it is recommended to place the pin on the intermediate certificate of the CA that issued the server certificate, to ease certificates renewals and rotations."
For more information on implementing and testing public key pinning you can refer Implementing and Testing HTTP Public Key Pinning (HPKP)
Your application can store multiple certificates in its pin list. The procedure for changing the cert would then be:
Some time before the certificate expires, release a new version of your app with a replacement cert in the pin list, as well as the original cert
when the old certificate expires, replace it on the server - the app should then still work as the new cert will already be in the pin list
Some time after the cert expires, release a new version of your app removing the old cert
Remember your users have to update the app before the old cert expires

How to protect calls to web services from being visible

im using silverlight 5 and WCF .. and the site is secured with HTTPS . however if i use fiddler , i can see this in the headers:
GET /ClientBin/XXXX-Web-MyService.svc/binary/GetUsers
if i put that directly after my domain : https://www.mydom.com/ClientBin/XXXX-Web-MyService.svc/binary/GetUsers
it will download all data from tabel users. how can i hide and protect this information from being visible!! isn't using SSL enought ? why is this visible anyways if im using https!?
thank you.
EDIT: my initial question was kind of an 'uneducated' one and for that i apologies,
i found more info on the subject and did more research. in this Q on SO there is an explanation to why fiddler is able to decrypt and view requests and responses sent over https.
What is point of SSL if fiddler 2 can decrypt all calls over HTTPS?
and to make things even more difficult, the common solution to this problem is using
"Certificate Pinning"
which requires the use of System.Net.ServicePointManager which is not included in the silverlight implementation of System.Net namespace.
so here i am stuck with an SSL cert. that i paid for that can be "cracked" by anyone with basic knowledge of web debugging.
From a purely Theoretical Computer Science point of view, what you are asking for is near impossible to actually impossible. You would need to implement a trusted platform to protect against the attack.
Now for the Science bit, Concentrate
Okay, so lets start with some basic theory. SSL and thus by extension HTTPS solves a very very specific problem. How do you communicate information over an unsecure NETWORK confidential information with a party you have never communicated with before. In this case, the emphasis is on NETWORK. It does so by solving two problems,
Authentication of the server (the server is who it says it is)
Asymmetric Encryption of key exchange
There is some overlap, to ensure that this is one step. I will focus on the 1st, as this is where fiddler "attacks" your system.
The SSL authentication works on a concept of a web of trust. Your computer has a list of TRUSTED verifiers. These are companies like Verisign, Thawte, Geotrust etc. These companies verify certificates by signing them (complex asymmetric encryption term, but its very like a handwritten signature, hard to forge, easy to verify).
Fiddler works by inserting a new trusted CA (verifier) into your computer. From then on, when you visit an HTTPS site, it will send requests on your behalf, reads it then forwards it back on to you with its OWN SIGNATURE. Since your computer completely trusts this signature, it thinks nothing is wrong.
Now, you want to implement certificate pinning. This IMHO is "bloody awful". It works by telling your software to expect a specific SSL cert. Two reasons why this is bad.
If I can work Fiddler, I can work dotPeek and recompile WITHOUT certificate pinning.
When your certificate gets revoked, your clients won't be able to connect.
Why would your certificate be revoked? If your CA loses their private keys, then they will be obliged to make sure its revoked and a replacement sent to you. Also each and every certificate has a sell by date as well, and must be replaced before they start to smell.
So finally what can you do?
SSL is NOT designed for protecting against what you are doing on your machine. The simpliest way to do what you are asking is to simply wrap your WCF calls in an extra layer of symmetric (or even asymmetric) encryption. But once again. The keys must live somewhere, so your client WILL be able to get the keys from a simple disassemble of your binaries and be able to construct a proxy of their own.
In conclusion
This is pretty much exactly the same as the DRM problem. You want to give your customer access to something on their machine but not show them how it works. If you do manage to solve this problem, do post a follow up, since Sony, Nintendo and Microsoft (to name a few) would be very interested in your findings.

Verifying A Server's Identity

What is the best means to verify that a server is who it says it is.
I'm guessing using signed SSL certs is the best route, but was wondering if there was any programmatic means to do this..
EDIT: This is for a an app where servers deal with other servers (authenticating each other) in order to exchange user info. (sorry if I forgot to mention that)
SSL certificates signed by an authorized CA (certificate authority) is the only way to be sure. Anything else can be faked, and especially any "programmatic means" would be particularly unreliable. Short and simple: an authorized SSL cert is the only thing a browser will recognize as reliable, regardless.
You don't need certificates to prove your identity (or a server's for that case) to someone. You can use pre-shared keys for that purpose, and avoid any public key infrastructure. The TLS (or SSL) protocol supports that. Find a TLS library that allows you to use TLS-PSK and use it.
I'd recommend HMAC or RSA. HMAC is pretty secure and much easier to implement. HMAC could get unwieldy if you have 5 servers that all need to communicate with each other directly.
What are you trying to secure? It sounds like a web application, and if it is one, then you should go with SSL certs.