Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Remote fonts... just a debate #506

Closed
crssi opened this issue Sep 14, 2018 · 21 comments
Closed

Remote fonts... just a debate #506

crssi opened this issue Sep 14, 2018 · 21 comments

Comments

@crssi
Copy link

crssi commented Sep 14, 2018

I know you hate fonts due to tracking and fingerprinting, but lets just a debate for someones that still uses fonts.

Lets say we don't care about IP.

Fingerprinting can be done over canvas, OS and UA.
Lets say that canvas is sorted out by FF and by CB WE.
We don't care about UA and OS and we do not spoof that, since its near to impossible to.

Then here is tracking. From what I see there are two vectors for that.
One is setting a cookie, which we don't care since we block 3rd party cookies.
Second is request header containing the Origin, from which the font provider, like EvilCorp, tracks your browsing sites.
We can neutralize origin using Header Editor WE:
Configure new rule as Modify the request header with Match type = All and Execute type = Custom function:

let isFont = false;
for (let a in val) {
    if (val[a].name.toLowerCase() === 'accept' && val[a].value.toLowerCase().substring(0,16) == 'application/font') { isFont = true; }
    if (isFont && val[a].name.toLowerCase() === 'origin') { val[a].value = ''; }
}

Is this good?
Do I miss something else?
Perhaps question for @earthlng: is upper code OK?

Cheers

@earthlng
Copy link
Contributor

that code only works if the origin header comes after the accept header (although that should probably almost always be the case). A more efficient and reliable way would be to check details.type for font and only run the loop in that case.
But some sites use a 3rd party css file which then loads the fonts. In that case the css would leak the origin while the font itself would only leak the origin of the css.

@crssi
Copy link
Author

crssi commented Sep 14, 2018

that code only works if the origin header comes after the accept header (although that should probably almost always be the case)

it is

A more efficient and reliable way would be to check details.type for font and only run the loop in that case.

not sure that I follow... do you mean with Header Editor?

But some sites use a 3rd party css file which then loads the fonts. In that case the css would leak the origin while the font itself would only leak the origin of the css.

Are you sure?
I have investigated quite a lot different font providers and origin was never set over css.
If it is set, then it is always over font.

@earthlng
Copy link
Contributor

  1. yes I mean with HE
  2. yes I'm sure. See fe https://developers.google.com/fonts/docs/getting_started

<link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Tangerine">

I'm sure that's what a lot of sites use because it's easy and is the 1st thing they list on that getting-started page

@earthlng
Copy link
Contributor

earthlng commented Sep 14, 2018

something like this should work for what you originally tried to do, just a lot more efficient and a bit more reliable:

if ('font' === details.type)
  for (let a in val) if (val[a].name.toLowerCase() === 'origin') val[a].value = '';

@crssi
Copy link
Author

crssi commented Sep 14, 2018

^^ Thank you for pointing this out. 😄
It doesn't work as is, but was a nice direction.
This works:

if (detail.type === 'font') {
   for (let a in val) {
      if (val[a].name.toLowerCase() === 'origin') { val[a].value = ''; }
   }
}

About CSS, I cannot find one sample that reveals the calling page. Its always font (if uses Origin) and never CSS.

@earthlng
Copy link
Contributor

no problem, you're welcome

re: css - you can find some example sites here: https://trends.builtwith.com/widgets/Google-Font-API

see under Site Totals, fe
https://trends.builtwith.com/widgets/Google-Font-API/United-States
https://trends.builtwith.com/widgets/Google-Font-API/United-Kingdom
etc

one example with a 3rd-party google css for fonts I just found in that list is https://www.dailystar.co.uk/

@crssi
Copy link
Author

crssi commented Sep 14, 2018

one example with a 3rd-party google css for fonts I just found in that list is https://www.dailystar.co.uk/

CSS still doesn't reveal Origin (that is the calling page).

Doesn't matter which site from upper lists I pick, I cannot find the example where Origin is exposed over CSS, as I said numerous time... its always font that is.

@crssi
Copy link
Author

crssi commented Sep 16, 2018

Separate from fonts, also script's and css's reveals your browsing over Origin quite often.
I am browsing now for a few days with:

if (detail.type === 'font' || detail.type === 'script' || detail.type === 'stylesheet') {
   for (let a in val) {
      if (val[a].name.toLowerCase() === 'origin') {
         val[a].value = '';
         break;
      }
   }
}

No breakages so far, will continue to use that and pay now attention also for XHR (I already know that EvilCorp's YT doesn't like removing origin from XHR).

Maybe the topic should change to: Tracking over header Origin

@KOLANICH
Copy link

KOLANICH commented Sep 16, 2018

Do I understand right that a font file on Windows is processed by system libs and eventually a kernel? Can a font be used as a crossapp (browser/pdf viewer/document viewer) kernel exploit vector?

@crssi
Copy link
Author

crssi commented Sep 16, 2018

^^ It has been seen a few times in a security history. AFAIK latest there is no known vector, which does not mean there is none and if there is/will be some kernel exploit then IMHO needs to be patched by OS security updates.
At start this topic was meant more about tracking... and it started with fonts, but from what I am seeing is not anymore just about fonts, but also about 3rd party scripts and 3rd party CSSs, and maybe also other resources too (XHR for sure need some more investigation).

At this point I am almost 100% certain that upper script does help preventing a lot of tracking, not covered before, immediately when fonts, JS and CSS are enabled.
I don't know any user, who disabled those, that would not enable it at some pages. And most of users I know, have all those constantly enabled.

@KOLANICH
Copy link

if there is/will be some kernel exploit then IMHO needs to be patched by OS security updates.

or doing font file processing and sanitizing purely in userland, which should prevent zeroday crossapp kernel exploits since kernel doesn't processes the stuff from the file directly, though there may be workarounds.

@crssi
Copy link
Author

crssi commented Sep 17, 2018

OT: FF is calling getpocket.cdn.mozilla.net every once and a while.

@Atavic
Copy link

Atavic commented Sep 21, 2018

@crssi It has some interaction with activity-stream:
#396

catchpoint/WebPageTest#1166
https://support.mozilla.org/en-US/questions/1198023

@earthlng
Copy link
Contributor

CSS still doesn't reveal Origin (that is the calling page).

Doesn't matter which site from upper lists I pick, I cannot find the example where Origin is exposed over CSS, as I said numerous time... its always font that is.

yeah sorry you're right. Using fe. <link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Tangerine"> doesn't produce a request where CSS leaks the origin. But the more elaborate <link crossorigin="anonymous" media="all" integrity="sha512..." rel="stylesheet" href="https://....css"> that for example github uses, does leak the origin in the CSS request. I see you already opened a new issue to discuss this further.

@Maryse47
Copy link

The template from #506 (comment) break icons in gitlab for me.

@crssi
Copy link
Author

crssi commented Sep 23, 2018

@Maryse47
URL to specific gitlab page?
If I visit https://gitlab.com/labwrat/Firefox-user.js/tree/master, all the icons are in place wherever I go.

@Maryse47
Copy link

Maryse47 commented Sep 23, 2018

Files/directories icons are broken in above url as well for me. Disabling that rule fixes it. The particular error is:
Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at https://assets.gitlab-static.net/assets/fontawesome-webfont-2adefcbc041e7d18fcf2d417879dc5a09997aa64d675b7a3c4b6ce33da13f3fe.woff2. (Reason: CORS header ‘Access-Control-Allow-Origin’ missing).[Learn More] Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at https://assets.gitlab-static.net/assets/fontawesome-webfont-ba0c59deb5450f5cb41b3f93609ee2d0d995415877ddfa223e8a8a7533474f07.woff. (Reason: CORS header ‘Access-Control-Allow-Origin’ missing).[Learn More] Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at https://assets.gitlab-static.net/assets/fontawesome-webfont-aa58f33f239a0fb02f5c7a6c45c043d7a9ac9a093335806694ecd6d4edc0d6a8.ttf. (Reason: CORS header ‘Access-Control-Allow-Origin’ missing).[Learn More]

@crssi
Copy link
Author

crssi commented Sep 24, 2018

Now I see it too. Damn 😢 . Thanks

@crssi
Copy link
Author

crssi commented Sep 24, 2018

@Maryse47
You can overcome this problem with additional rule to neutralize Access-Control-Allow-Origin in the response header, effectively to eliminate CORS. But I don't think, at the moment, that action is wise to do.
Will dig into some more in the next days or so.

@Maryse47
Copy link

@crssi great, thanks.

@crssi
Copy link
Author

crssi commented Sep 25, 2018

@Maryse47
Add new "Modify response header" with a script:

if (detail.type === 'font' || detail.type === 'script' || detail.type === 'stylesheet') {
   for (let a in val) {
      if (val[a].name.toLowerCase() === 'access-control-allow-origin') { return; }
   }
   val.push({'name': 'Access-Control-Allow-Origin', 'value': detail.originUrl.split('/', 3).join('/')});
}

What we do here is to check if CORS is set.
If it is set then we do not change a thing.
If is is not set, then we set it to the schema+domain of the response server.

We might get some better performance with regex.

Since this issue is closed, I will duplicate the answer at #509 today where you should also continue this conversation.

Note: This rule is addition to the "Modify request header" as healer process.

Cheers

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Development

No branches or pull requests

5 participants