SSL without a certificate - codeigniter

I am developing a backend section for a company where they need as much security as possible because they will put sensible information in it.
They asked me to add SSL, which I added(the website is coded in codeigniter) but I don't know if a SSL certificate is really needed.
Having in mind that this website will only be accesible by a set of two different IPs, the two offices they have I don't think getting a certificate would be needed. Am I right?
Edit 24 Feb:
The data has the information of projects, list of clients so it is sensitive.
So I think I will go with a self signed ssl.
Thank you all

There are a few other issues you should keep in mind, in addition to those who have previously answered:
Will the users of this site be connecting and transferring this sensitive information over a wireless connection at any point in time? If this is the case, then yes, you need SSL.
HTTPS is not such a burden on server resources as it once was. Especially with a site only being used by a limited number of users at defined locations, you should certainly be able to provide for the maximum number of users.
If this is a private site, and cost is an issue, go with a self-signed certificate. The OpenSSL toolkit is your best bet for this. Numerous guides for setting up self-signed certificates with OpenSSL are available.
Are there legal issues involved with this sensitive data? If you are transmitting customer information in a client database with phone numbers, postal addresses, email addresses, login information - or even more seriously, credit card numbers - then you need SSL. Ask yourself if you would trust a company who transmitted this same information of yours without SSL.
If the client asked for it and is paying for it, this isn't an undue burden on you as a developer, and as a developer you really never want to be in the position where you're arguing for less security. If there's a problem later, it comes back to bite you. Cover your rear end.
Combine this with IP restricted access. If you can, do that at the Apache configuration level. If not, then do it with a .htaccess. Why at the Apache level? Again, that covers your rear end in case you forget to put the restrictions in a .htaccess, or in case someone else comes in and removes them by accident.
If there's even a question about it, use SSL.

SSL certificate is needed because somebody could read the request content on the way to your server. You can't add https to the web page without certificate (check if you have https protocol in the browser page address).
In developing stage you can generate SSL certificate by yourself (use openssl) there is no need to buy valid one. There will be warning in the browser that the certificate is not signed by any authority, but I don't think that is big problem.

If you need to protect clinet-server communication (http request/response headers and data) from being overheard, then you need to install SSL on your sever, and use https protocol. This is useful when you want to hide i.e. user credentials.
If it is just about allow/disable access for mentioned ip addresses, than it is enough to limit it in http server configuration (usually .htaccess).
Please keep in mind, that https requests requires more server/client resources (CPU), so it should not be used if not necessary.

Related

Guzzle disabling certificate verification to false, how insecure is it?

Recently I found myself working with Guzzle while making requests to another server to post and fetch some data, in some cases, tokens. But I was getting certificate invalid error and I even tried to get a new .pem certificate, but Guzzle was still not accepting and kept throwing that error. So finally, I did what the "Internet" said:
$guzzleClient = new Client([
'verify' => false
]);
Now although this solution works, I am not sure how insecure it can get. Do I need to worry? If yes, in what scenarios?
well this is a big problem if you are for example
having login system on the request you are sending using guzzle
having payment/checkout on the request
basically any sensitive data being passed to the other server
because when you pass data without SSL certificate then your requests might get caught by malicious programs like
BurbSuite / WireShark , cain and abel / EtterCap
as these programs are Sniffing programs and anyone can get a version from the internet as they are open sourced and every thing going without SSL can be intercepted by the hacker using the tools mentioned above and the hacker can look to the entire request in plaintext! so its highly recommended to use SSL connection when passing sensitive data
Worth Mentioning : now a days even SSL isn't very secure because hackers can remove it using SSLStrip tool but believe me SSL will make it much harder for them to get to your request because if they used it your website sometimes will make non-completed requests and it will notify the user that the network isn't secure this will make it very hard for the hacker to get the user's data,
TLS/SSL in common configurations is meant to give you three things:
confidentiality - no third party is able to read the messages sent and received,
integrity - no third party is able to modify the messages sent and received,
server authentication - you know who are you talking to.
What you do with setting verify to false is disabling the certificate verification. It immediately disables the server authentication feature and enables loosing confidentiality and integrity too when facing an active attacker that has access to your data stream.
How is that?
First of all TLS/SSL relieas on Public Key Infrastructure. Without going into too much details: you hold on your machine a set of certificates of so called Certification Authorities (CA) whom you trust. When you open a new communication to a service, you get the services certificates and in the process of verification you validate amongst other things if the certificate belongs to a CA you trust. If yes, then the communication may proceed. If no, then the communication channel is closed.
Attack patterns
Disabling certificate verification allows for Man-in-the-Middle (MitM) attacks than can easily be performed in your local network (e.g. via ARP poisoning attacks), in the local network of the service you are calling or in the network between. As we usually do not trust the network completely, we tend to verify.
Imagine me performing an attack on you. I have performed ARP poisoning, now I can see all your traffic. It's encrypted, isn't it? Well, not obviously. The TCP handshake and TLS handshake you believe you have performed with the target service - you have performed with me. I have presented you not the certificate of the target service, as I am unable to fake it, but my own. But you did not validate it to reject it. I have opened a connection between me and the target service on your behalf too so I can look into the decrypted traffic, modify if necessary and reply to you to make you believe everything is ok.
First of all - all your secrets are belong to me. Second of all - I am able to perform attacks on both you and the target service (which might have been secured by authentication mechanisms, but now is not).
How to fix this?
In XXI century there should be little reason to disable TLS verification anywhere. Configuring it to work properly might be a pain though, even more when you are doing it for the first time. From my experience the most common issues in the micro service world are:
the target certificate is self-signed,
you are missing a CA root certificate in your trust store,
the microservice does provide his certificate, but does not provide an intermediate CA certificate.
It's hard to guess what your issue is. We would need to dig deeper.
While the other answers points out some really good point about how important SSL/TLS is, your connection is still encrypted and the remote endpoint you're using has https:// in it as well. So you're not entirely disabling SSL when you set verify to false if I'm not mistken. It's just less secure since that you're not verifying the certificate of the remote server if they are signed by a Certificate Authority (CA) using the CA bundle.
Do you need to worry?
If this is something on your production, ideally you'd want things to be secure and configured correctly, so yes.
By not verifying the certificate, like Marek Puchalski mentioned, there's possibility of the server might not be the one you think it is and allows mitm (man in the middle) attack as well. More about mitm here, and peer verification here.
Why is it happening & how do you fix it?
Most common issue is misconfigured server, especially PHP configuration. You can fix your PHP configuration following this guide, where you'll be using adding the CA root certificates bundle to your configuration. Alternatively you can add this to Guzzle.
Another common issue is, the remote server is using a self-signed certificate. Even if you configured your CA bundle in your trustedstore, this certificate can't be trusted since it's not signed by a trusted CA. So the server needs to configure a SSL certificated signed by a CA. If that's not possible, you can manually trust this CA root, however this comes with some security concerns as well.
Hope this helped :)

Does updating SNI config affect SSL Certificates and Validation

I'm developing an app for a non-tech client that has outsourced the backend to another developer. We'll be launching the app under 7 different branded app, over a series of weeks. Each app is exactly the same, sans for the domain the API end points are on (IIS hosted).
As part of our security, we validate the SSL certificate when we connect to the API, and ensure the key returned by the API server matches our hardcoded version of it, as to prevent man-in-the-middle attacks to sniff our REST calls. We have this functioning now for the current server (1 of 7 to be rolled out).
We've asked the backend guys to provide the certificates for the remaining 6 sites, so we can deploy the apps with the expected keys. However, they claim that as they will be rolling out the sites individually over the coming weeks, each time they bring a new a new site online, they said they are "updating the SSL certificate" which is required as they are "using SNI on the server, so each time a new site is added, the certificate will change, and the hardcoded validation for the existing sites will break".
Now whilst I'm no dummy, I'm also not a server admin, and only 99.9% sure that the SNI configuration to support another cert on the server, will not have any affect on the current certs already hosted for the existing domains. As a result, I wanted to explicitly confirm that the cert key we're validating as part of the SSL auth, is not going to change with each revision of the SNI config. The backend devs have essentially shut us down claiming we're paranoid, and going "beyond what is required" and to not expect "the same security a the major players offer" (as I mentioned that any decent commercial app validates its connection).
Is anyone able to confirm (or correct) my understanding of SNI as it relates to the certs, primarily that as they bring new sites online, that changes to the SNI have 0 impact on the existing certs for the current sites?
Edit: Whilst the use of multi-domain certs would regenerate the key, we can assume that they could generate/re-issue a multi-domain cert now in advance of the domains coming online. The question of if it's affected by the SNI config remains.
"updating the SSL certificate" which is required as they are "using SNI on the server, so each time a new site is added, the certificate will change, and the hardcoded validation for the existing sites will break".
This is a weird argument. The point of SNI is that they can have multiple sites (domains) on the same IP address where each has its own certificate. If they add a new site only a new certificate for the new domain need to be created and all the other certificates will continue to work: a client using SNI will tell which site it wants to visit and the server then can pick the appropriate certificate. If they instead could not rely on SNI then they would have to use certificates which cover all sites on the same IP address.
So while it can be that they have some process which requires this kind of reissuing certificates it is not a requirement because of use of SNI, but only because they designed their process this way.

Securing communication on a portable intranet (changing IP addresses)

I have the following scenario:
A network will be set up on a Windows infrastructure
A website will be put on that network - It is not given a domain name and is not available on the internet. It will be addressed only via an internally recognised IP address.
A piece of software within that network will communicate with the website
(we want to avoid the 'Could not establish trust relationship issue' found with self-signed certificates without reducing security as, I believe, the accepted answer does).
The website will also be viewed on tablets and PCs.
After a few days, the service will be be put on a different network (with different IPs).
It will installed on many PCs/Networks.
I want to secure this via SSL, but it seems tricky following the 2015 update that disallowed IP addresses to have certificates.
This post suggests going via a public IP, but the solution may be completely offline in an area without internet access.
I've spent hours researching, but seem to be missing something.
How should this be done please?
I would setup a DNS server with an app.local domain that gets issued the certificate.
Even if you serve up the intermediate certificates in the TLS handshake (which you should ALWAYS do and not rely on AIA), verifying the chain becomes problematic without Internet access as browsers won't be able to reach the CRL URL (Certificate Revocation List). That is, of course, unless we're talking about your own CA (living in the same network) that issues the site certificate.
If everything you describe runs in a well guarded sandbox then you probably don't need the TLS layer at all, ask yourself WHO is the attacker and WHAT are you protecting.

Shipping SSL certificate in Mac OS X app

I'm writing a utility Mac OS X app that basically acts as a web server accepting incoming HTTP requests (think of it as a mock REST API server). I want to be able to support HTTPS, but ideally I'd like to remove the requirement for my users to have to purchase their own SSL certificates.
I've been thinking a little on how I might achieve this. Let's say I register a domain called myapp.com. I then purchase an SSL cert for myserver.myapp.com that is signed by a registered CA. I ship my app with those SSL cert details embedded within it. All my users have to do is update their /etc/hosts file to point myserver.myapp.com to whatever IP address my app is installed and running on.
In fact, by far, the most common scenario would be my app running on the same machine as the client, so I'm considering updating the main DNS entry for myserver.myapp.com to point to 127.0.0.1, and most users wouldn't have to change anything.
So, that's the basic theory. What have I missed that would make this an unworkable plan? A couple of things that have crossed my mind:
I could use a self-signed cert. However, many SSL clients barf (or throw up warnings) if the cert doesn't have a valid CA chain. I'm happy to pay the money for a real cert to alleviate this inconvenience for my users.
I would be embedding the private key for my SSL cert into my app. In theory, someone could extract that and use it to impersonate my app. I guess my reaction is "so what?" My app is a small productivity app, it isn't an e-commerce site. It doesn't collect sensitive info. It literally just simulates web server responses so devs can test their apps.
Any advice/feedback would be greatly appreciated. Thanks.
This won't work - but for nontechnical reasons.
Distributing an SSL certificate to your users along with its associated key will violate the issuance terms of your SSL certificate provider, and they will revoke the certificate when they discover what you have done. (This happened, for example, when Pivotal tried to offer SSL service for developers through sslip.io.) This will, of course, cause your application to stop working.
If your users have administrative access to their machines, they can create and trust their own self-signed CA using Keychain Access. Once they have done so, they could create a certificate (again, using Keychain Access) and insert that into your application to enable SSL.
As said in the other answer you can't ship the same certificate for everybody. What you could do is generate different for everybody:
The application ask them the domain name they want to use (a domain they must own, like myapp.example.com)
The application use the ACME protocol to get automatically a trusted certificate from let's encrypt
Note: you can provide them subdomains of a domain you control (like [clientid].yourappname.yourdomain.com) ONLY of you can register yourappname.yourdomain.com in the public suffix list (because let's encrypt have rate limits)

How to prevent HTTPS man-in-middle attack from the server side?

In the HTTPS security model, the weakest part is the list of trusted CA in the browser. There are many ways that someone could inject addition CA to the list that users will trust the wrong guy.
For example, a public computer, or PC in your company. The administrator could force you to trust a CA issued by himself, it could be very insecure with a HTTPS proxy server with HTTPS relay. As a result, they will able to SPY your message, login, and password even browser tell you that your are on trusted SSL connection.
In this case, what can web application developer could do to protect user and also the system?
As a web application developer there is very little you can do about this.
This issue needs to be dealt with further down the stack.
If someone half way around the world wants to:
a. Put a false root CA on someone's computer
b. Issue a cert for your domain under that CA
c. Impersonate your site
d. Point someone's local DNS entry for your domain to a different ip
In none of the above steps is your application involved or consulted so this is where good network administration and security is important.
Aside from that, maybe there's a legitimate reason for someone to do just this locally on their personal network. Who am I to stop them?
This is essentially what corporate web proxy filters do and they are within their rights to do it.
As far as stopping someone malicious from taking the above steps thats something that needs to be put on the administrators of your customers machines.
Theoretically speaking, if the user's terminal is owned by an adversary, you've already lost and there's nothing you can do about it -- if push comes to shove they can filter out your countermeasures or even scrape and spoof the entire site.
In practice, you can do things to make the adversary's job harder, but it's an arms race. You'll likely have to use all the same sorts of countermeasures that malicious software uses against scanners -- because from the adversary's point of view your site is behaving maliciously by trying to prevent itself from being overridden! -- and know that anything you do can and will be rapidly countered if your adversary cares enough.
You could, for example, open sockets or useXmlHttpRequest from JavaScript or applets, but you can't stop your adversary from updating their filters to strip out anything you add.
You might get more mileage by emitting polymorphic output or using other anti-reverse-engineering techniques, so it appears that no two hits to the site produce similar code/resources sent to the browser. It's an inordinate amount of work but gives your adversary a puzzle to chew on if they want to play man in the middle.

Resources