I am developing a firefox addon, and I need to make https calls. I am given an SSL certificate information (Serial Number, SHA1 Fingerprint, andMD5 Fingerprint). When I try to use the Request module from my main.js I always get a status of 0. I tried the Request module with other http requests which are not secured and it works fine.
So I assume that the 0 status has to do with the SSL certificate.
Although I try to simulate the same requests using Dev-HTTP-Client google chrome plugin and it works fine and I can get proper responses from the https server.
I am not sure but I think I need to use the chrome module Cc["#mozilla.org/security/... to make this work.
If you can guide me with the proper steps to setup the SSL certificate information from inside the addon that would be great
Unfortunately there is no direct way to verify a cert manually and continue with the request. Instead you need to add an override on error yourself and retry.
Attempt to make a regular XMLHttpRequest via nsIXMLHttpRequest. There is enough code and samples around on SO and Google describing how to do it. The requests module won't do, as it hides some necessary details.
Implement nsIBadCertListener2 and stuff it into req.channel.notificationCallbacks (might want to preserve the original callbacks).
If your .notifyCertProblem() get called, that means the cert did not verify. Now it's up to you to verify the cert with your seeded fingerprint (and serial).
If your seeded infos match, add a cert override (that won't work for STS hosts, of course)
Re-spin the request after adding the override, as the first request already got canceled as soon as it hit notifyCertProblem().
Most of the stuff is neatly demonstrated in ErrorPage.jsm of Boot2Gecko (still applies to all other mozilla powered products). That's a cross reference, so click around ;)
Of course, you'll need to use the chrome module.
I should mention that it is deliberate that I'm not giving a complete copy-pasta code solution, only all required pointers, as it is my opinion that a person should be capable enough to work with what I provided, or don't touch security subsystems in the first place.
Related
I had asked a question a while back about What is the difference between requiring an SSL cert and accepting an SSL cert?
For the most part that cleared up the differences between the two, however I am still a little unclear on the topic.
I have a few questions about this image:
Require SSL - What exactly does this mean from a client standpoint? Does it mean that in order for the webpage to appear the server needs to have an SSL certificate? How does this encryption work?
Client Certificates - I get that this all comes from the client, but is it something that I, as a webserver, would issue? What would be a particular situation where you would require a Client certificate?
Was also reading this article: Why SSL? The Purpose of using SSL Certificates
and while I do have Require SSL and Ignore Client certificates setup on specific pages, I don't see the below changes to the address bar:
Why do I not see that? What is required of me in order to get that working, because that leads me to believe there really isn't anything more secure with using HTTPS as opposed to HTTP
The reason that I am questioning this is because recently, when trying to dynamically load HTML into my website I was doing the loading using Javascript and HTTPS for the url, but I was getting domain errors saying that it was not coming from the same origin...
i.e. http://www.example.com & https://www.example.com - I don't get why I would get an error saying not the same origin? Not to mention I was also using the page with HTTPS (that is what was present in the address bar). Meanwhile while changing the link to HTTP seemed to fix that error.
Require SSL - What exactly does this mean from a client standpoint?
The documentation is a little unclear. It either means:
When a plain HTTP request is made to the server, it responds saying "The resource you want is at this HTTPS URL, go there to get it" or
It turns off plain HTTP support entirely
This is easy to test if you have an IIS server which supports SSL (I don't) and I would assume it is the first option.
Client Certificates - I get that this all comes from the client, but is it something that I, as a webserver, would issue? What would be a particular situation where you would require a Client certificate?
Generally, you would issue them in the capacity of "someone running a webserver, but possibly also other systems, which require a client certificate".
You use these in lieu of a username/password.
while I do have Require SSL and Ignore Client certificates setup on specific pages, I don't see the below changes to the address bar
It is hard to tell what the issue is when you don't show us what you see on your own site.
i.e. http://www.example.com & https://www.example.com - I don't get why I would get an error saying not the same origin?
The rules for origins are quite strict.
The hostname must be the same (it is)
The port must be the same (it isn't, you have 80 and 443, which are the defaults for HTTP and HTTPS)
The scheme must be the same (HTTP and HTTPS are not the same)
You should mitigate this by using SSL everywhere. Don't use plain HTTP for some things and HTTPS for others.
It's possible that the lack of notification from the browser that the connection is secure (as mentioned in the previous section) is due to you loading other resources over HTTP into the page, but without a test case it is hard to tell.
The Very Short Version: is anybody successfully requesting local resources via AJAX, in IE, over SSL? I cannot solve getting an "access denied" error.
The Longer Version:
I am using AJAX to retrieve JSON from an application that runs a local web service. The web service channel is encrypted so that if the remote site is being served over HTTPS, no "insecure resource on a secure page" errors appear.
So, in the address bar is a remote site of some sort... mysite.com. It is receiving information from https://localhost/.
The web service is setting correct headers for CORS and everything works in Chrome and Firefox. In IE, if I put my https://localhost resource into the address bar, the correct resource is returned and displayed. However, when using AJAX (not just the address bar), a security setting in IE is denying access. This is documented (in part) here:
Access denied in IE 10 and 11 when ajax target is localhost
The only proper solution in one reply is to add the requesting domain (mysite.com in this case) to the trusted sites. This works, but we would prefer to not have user intervention... pointing to a knowledge base article on how to add a trusted site is hardly a great user experience. The other replies to that question are invalid for the same reasons as below-->
Some more stumbling around and I discovered this:
CORS with IE, XMLHttpRequest and ssl (https)
Which had a reply containing a wrapper for AJAX requests in IE. It seemed promising, but as it turns out, IE11 has now deprecated the XDomainRequest API. This was probably the right thing for Microsoft to do... but now the "hack" workaround of adding a void onProgress handler to the XDR object is obviously not an option and the once-promising workaround wrapper is rendered null and void.
Has anybody come across either:
a) a way to get those requests through without needing to modify the trusted sites in IE? In other words, an updated version of the workaround in the second link?
b) as a "next best" case: a way to prompt the user to add the site to their trusted zone? "mysite.com wishes to be added to your trusted zones. Confirm Yes/No" and have it done, without them actually needing to open up their native settings dialogues and doing it manually?
For security reasons, Internet Explorer's XDomainRequest object blocks access (see #6 here) to the Intranet Zone from the Internet Zone. I would not be surprised to learn that this block was ported into the IE10+ CORS implementation for the XMLHTTPRequest object.
One approach which may help is to simply change from localhost to 127.0.0.1 as the latter is treated as Internet Zone rather than Intranet Zone and as a consequence the zone-crossing is avoided.
However, you should be aware that Internet Explorer 10+ will block all access to the local computer (via any address) when a site is running in Enhanced Protected Mode (EPM)-- see "Loopback blocked" in this post. Currently, IE uses EPM only for Internet sites when run in the Metro/Immersive browsing mode (not in Desktop) but this could change in the future.
No, there's no mechanism to show the Zones-Configuration UI from JavaScript or to automatically move a site from one zone to another. However, the fact that you have a local server implies that you are running code on the client already, which means you could use the appropriate API to update the Zone Mapping on the client. Note that such a change requires that you CLEARLY obtain user permission first, lest your installer be treated as malware by Windows Defender and other security products.
So, in summary, using the IP address should serve as a workaround for many, but not all platforms.
Since those are two different domains, one solution would be to create an application which proxies the requests in the direction you want.
If you have control over the example.com end, and want to support users who bring their own localhost service, this would be harder, as you would have to provide more requirements for what they bring.
If however, you have control over what runs in localhost, and want to access example.com, and have it access the localhost service, set up redirection in your web server of preference, or use a reverse proxy. You could add an endpoint to the same localhost app which doesn't overlap paths, for example, route http://localhost/proxy/%1 to http://%1, leaving the rest of localhost alone. Or, run a proxy on e.g. http://localhost:8080 which performs a similar redirection, and can serve example.com from a path, and the API from another.
This winds up being a type of "glue" or integration code, which should allow you to mock interactions up to a point.
I have a site which makes AJAX JSONP calls to a secured (SSL) web server. If I use a unsecured (HTTP) web server , everything works fine, but when I change to the SSL version, the call never returns. I've checking with fiddler and the error is following:
The remote server (192.168.150.85) presented a certificate that did not validate, due to RemoteCertificateChainErrors.
This means that some intermediate certificate is missing, but I don't know which one. In any case I need to deal with the situation where some installations has invalid certificate credentials.
It is known, that if you try to execute an AJAX method against a secure URL with a non-trusted or expired certificate the browser will warn your user about that, regardless of how or what you're trying to do. In browser you can accept the risks, even in C# you can implement a callback to accept these risks as well. But I don't know how to do it in Javascript/JQuery.
Do someone have an idea about how to handle this situation?
Thanks!
It seems that this is not possible/recommended. It is indeed not a good idea. We work now with real certificates which is quite cheap (there are even free ones) and easier to manage in our test environment, where we have several mobile devices, types of clients and so on.
I am trying to accomplish some specific test requirement.
One of the requirement now is to redirect some nonexistent url to specific ip, which is what the dns is doing. I think firefox is using internal dns cache. But I cannot find a proper service that I can use to change such kind of dns cache. On the other hand, i have no idea if firefox support some kind of service to customize the dns process, I mean give a customized result instead of really getting from DNS Server.
As I need to start many firefox process to do the work concurrently, so I cannot do this simply by changing the system hosts file, cause it will affect other process.
Any idea?
No, modifying DNS responses isn't possible in Firefox, the DNS service merely allows triggering a DNS request. What you could do is recognizing NS_ERROR_UNKNOWN_HOST response and somehow redirecting it to your server. While recognizing isn't particularly hard, redirecting is complicated. You could add a progress listener and check whether a request finished in onStateChange method (if (aFlag & STATE_STOP)). The parameter aStatus gives you the status of the request, you would be looking for status Components.results.NS_ERROR_UNKNOWN_HOST. And for top-level requests (aFlag & STATE_WINDOW) you could change window location to make a request to a different server instead. For other requests - don't know how one would "redirect" there.
so I have been having trouble with grabbing information from a device that is interfaced with via https due to the fact that it has an invalid security certificate. I know the device is to be trusted and I don't have access to the server-side so I can't change it. I was wondering if there was any way to set up an XMLHttpRequest object in Javascript to just ignore an invalid SSL certificate and just grab the information anyway. As it is now it seems to just reject the certificate and stop. Thanks.
Well I had found this solution before but it didn't work, this was because I was still using actual XMLHttpRequest though. When creating it using this statement:
httpreq = new ActiveXObject("Msxml2.ServerXMLHTTP.3.0");
There is a method called setOption that is opened up for use:
httpreq.setOption(2, 13056);
With those parameters, the request now ignores the invalid certificate and grabs the information anyway. If I understand correctly this won't work with any non-Microsoft technology trying to run the script, but that's ok for the scope of my project.
No, there isn't. XMLHTTPRequest doesn't allow you to override that. Being able to override SSL security might make sense in your case, but if you think about it, it would be a bad idea in general. You'd never want to allow arbitrary javascript code on the internet to connect to a supposedly secure service that the js host (the browser) knows has a possible MITM issue.
I know the device is to be trusted
Yes but you don't know whether you are really connected to the device.
That is the purpose of the certificate. That's why it has to be valid.