Project

General

Profile

« Previous | Next » 

Revision 53837634

Added by koszko about 2 years ago

enable whitelisting of `file://' protocol\n\nThis commit additionally also changes the semantics of triple asterisk wildcard in URL path.

View differences:

content/main.js
10 10
 * IMPORTS_START
11 11
 * IMPORT handle_page_actions
12 12
 * IMPORT extract_signed
13
 * IMPORT sign_data
13 14
 * IMPORT gen_nonce
14 15
 * IMPORT is_privileged_url
15 16
 * IMPORT mozilla_suppress_scripts
......
31 32
    parent.hachette_corresponding.appendChild(clone);
32 33
}
33 34

  
34
if (!is_privileged_url(document.URL)) {
35
    /* Signature valid for half an hour. */
36
    const min_time = new Date().getTime() - 1800 * 1000;
35
function extract_cookie_policy(cookie, min_time)
36
{
37 37
    let best_result = {time: -1};
38 38
    let policy = null;
39 39
    const extracted_signatures = [];
40
    for (const match of document.cookie.matchAll(/hachette-(\w*)=([^;]*)/g)) {
40

  
41
    for (const match of cookie.matchAll(/hachette-(\w*)=([^;]*)/g)) {
41 42
	const new_result = extract_signed(...match.slice(1, 3));
42 43
	if (new_result.fail)
43 44
	    continue;
......
56 57
	policy = new_policy;
57 58
    }
58 59

  
60
    return [policy, extracted_signatures];
61
}
62

  
63
function extract_url_policy(url, min_time)
64
{
65
    const [base_url, payload, anchor] =
66
	  /^([^#]*)#?([^#]*)(#?.*)$/.exec(url).splice(1, 4);
67

  
68
    const match = /^hachette_([^_]+)_(.*)$/.exec(payload);
69
    if (!match)
70
	return [null, url];
71

  
72
    const result = extract_signed(...match.slice(1, 3));
73
    if (result.fail)
74
	return [null, url];
75

  
76
    const original_url = base_url + anchor;
77
    const policy = result.time < min_time ? null :
78
	  JSON.parse(decodeURIComponent(result.data));
79

  
80
    return [policy.url === original_url ? policy : null, original_url];
81
}
82

  
83
function employ_nonhttp_policy(policy)
84
{
85
    if (!policy.allow)
86
	return;
87

  
88
    policy.nonce = gen_nonce();
89
    const [base_url, target] = /^([^#]*)(#?.*)$/.exec(policy.url).slice(1, 3);
90
    const encoded_policy = encodeURIComponent(JSON.stringify(policy));
91
    const payload = "hachette_" +
92
	  sign_data(encoded_policy, new Date().getTime()).join("_");
93
    const resulting_url = `${base_url}#${payload}${target}`;
94
    location.href = resulting_url;
95
    location.reload();
96
}
97

  
98
if (!is_privileged_url(document.URL)) {
99
    let policy_received_callback = () => undefined;
100
    let policy;
101

  
102
    /* Signature valid for half an hour. */
103
    const min_time = new Date().getTime() - 1800 * 1000;
104

  
105
    if (/^https?:/.test(document.URL)) {
106
	let signatures;
107
	[policy, signatures] = extract_cookie_policy(document.cookie, min_time);
108
	for (const signature of signatures)
109
	    document.cookie = `hachette-${signature}=; Max-Age=-1;`;
110
    } else {
111
	const scheme = /^([^:]*)/.exec(document.URL)[1];
112
	const known_scheme = ["file"].includes(scheme);
113

  
114
	if (!known_scheme)
115
	    console.warn(`Unknown url scheme: \`${scheme}'!`);
116

  
117
	let original_url;
118
	[policy, original_url] = extract_url_policy(document.URL, min_time);
119
	history.replaceState(null, "", original_url);
120

  
121
	if (known_scheme && !policy)
122
	    policy_received_callback = employ_nonhttp_policy;
123
    }
124

  
59 125
    if (!policy) {
60
	console.warn("WARNING! Using default policy!!!");
126
	console.warn("Using default policy!");
61 127
	policy = {allow: false, nonce: gen_nonce()};
62 128
    }
63 129

  
64
    for (const signature of extracted_signatures)
65
	document.cookie = `hachette-${signature}=; Max-Age=-1;`;
66

  
67
    handle_page_actions(policy.nonce);
130
    handle_page_actions(policy.nonce, policy_received_callback);
68 131

  
69 132
    if (!policy.allow) {
133
	if (is_mozilla) {
134
	    const script = document.querySelector("script");
135
	    if (script)
136
		script.textContent = "throw 'blocked';\n" + script.textContent;
137
	}
70 138
	const old_html = document.documentElement;
71 139
	const new_html = document.createElement("html");
72 140
	old_html.replaceWith(new_html);

Also available in: Unified diff