| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 var logging = requireNative('logging'); |
| 6 |
| 5 /** | 7 /** |
| 6 * Returns a function that logs a 'not available' error to the console and | 8 * Returns a function that logs a 'not available' error to the console and |
| 7 * returns undefined. | 9 * returns undefined. |
| 8 * | 10 * |
| 9 * @param {string} messagePrefix text to prepend to the exception message. | 11 * @param {string} messagePrefix text to prepend to the exception message. |
| 10 */ | 12 */ |
| 11 function generateDisabledMethodStub(messagePrefix, opt_messageSuffix) { | 13 function generateDisabledMethodStub(messagePrefix, opt_messageSuffix) { |
| 12 var message = messagePrefix + ' is not available in packaged apps.'; | 14 var message = messagePrefix + ' is not available in packaged apps.'; |
| 13 if (opt_messageSuffix) message = message + ' ' + opt_messageSuffix; | 15 if (opt_messageSuffix) message = message + ' ' + opt_messageSuffix; |
| 14 return function() { | 16 return function() { |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 58 * preferred. | 60 * preferred. |
| 59 * @param {string} objectName The display name to use in the error message | 61 * @param {string} objectName The display name to use in the error message |
| 60 * thrown by the stub (this is the name that the object is commonly referred | 62 * thrown by the stub (this is the name that the object is commonly referred |
| 61 * to by web developers, e.g. "document" instead of "HTMLDocument"). | 63 * to by web developers, e.g. "document" instead of "HTMLDocument"). |
| 62 * @param {Array<string>} methodNames names of methods to disable. | 64 * @param {Array<string>} methodNames names of methods to disable. |
| 63 * @param {Boolean} useThrowingStubs if true, the replaced methods will throw | 65 * @param {Boolean} useThrowingStubs if true, the replaced methods will throw |
| 64 * an error instead of silently returning undefined | 66 * an error instead of silently returning undefined |
| 65 */ | 67 */ |
| 66 function disableMethods(object, objectName, methodNames, useThrowingStubs) { | 68 function disableMethods(object, objectName, methodNames, useThrowingStubs) { |
| 67 $Array.forEach(methodNames, function(methodName) { | 69 $Array.forEach(methodNames, function(methodName) { |
| 70 logging.DCHECK($Object.getOwnPropertyDescriptor(object, methodName), |
| 71 objectName + ': ' + methodName); |
| 68 var messagePrefix = objectName + '.' + methodName + '()'; | 72 var messagePrefix = objectName + '.' + methodName + '()'; |
| 69 object[methodName] = useThrowingStubs ? | 73 $Object.defineProperty(object, methodName, { |
| 70 generateThrowingMethodStub(messagePrefix) : | 74 configurable: false, |
| 71 generateDisabledMethodStub(messagePrefix); | 75 enumerable: false, |
| 76 value: useThrowingStubs ? |
| 77 generateThrowingMethodStub(messagePrefix) : |
| 78 generateDisabledMethodStub(messagePrefix) |
| 79 }); |
| 72 }); | 80 }); |
| 73 } | 81 } |
| 74 | 82 |
| 75 /** | 83 /** |
| 76 * Replaces the given properties of the passed in object with stubs that log | 84 * Replaces the given properties of the passed in object with stubs that log |
| 77 * 'not available' warnings to the console and return undefined when gotten. If | 85 * 'not available' warnings to the console and return undefined when gotten. If |
| 78 * a property's setter is later invoked, the getter and setter are restored to | 86 * a property's setter is later invoked, the getter and setter are restored to |
| 79 * default behaviors. | 87 * default behaviors. |
| 80 * | 88 * |
| 81 * @param {Object} object The object with properties to disable. The prototype | 89 * @param {Object} object The object with properties to disable. The prototype |
| 82 * is preferred. | 90 * is preferred. |
| 83 * @param {string} objectName The display name to use in the error message | 91 * @param {string} objectName The display name to use in the error message |
| 84 * thrown by the getter stub (this is the name that the object is commonly | 92 * thrown by the getter stub (this is the name that the object is commonly |
| 85 * referred to by web developers, e.g. "document" instead of | 93 * referred to by web developers, e.g. "document" instead of |
| 86 * "HTMLDocument"). | 94 * "HTMLDocument"). |
| 87 * @param {Array<string>} propertyNames names of properties to disable. | 95 * @param {Array<string>} propertyNames names of properties to disable. |
| 96 * @param {?string=} opt_messageSuffix An optional suffix for the message. |
| 97 * @param {boolean=} opt_ignoreMissingProperty True if we allow disabling |
| 98 * getters for non-existent properties. |
| 88 */ | 99 */ |
| 89 function disableGetters(object, objectName, propertyNames, opt_messageSuffix) { | 100 function disableGetters(object, objectName, propertyNames, opt_messageSuffix, |
| 101 opt_ignoreMissingProperty) { |
| 90 $Array.forEach(propertyNames, function(propertyName) { | 102 $Array.forEach(propertyNames, function(propertyName) { |
| 103 logging.DCHECK(opt_ignoreMissingProperty || |
| 104 $Object.getOwnPropertyDescriptor(object, propertyName), |
| 105 objectName + ': ' + propertyName); |
| 91 var stub = generateDisabledMethodStub(objectName + '.' + propertyName, | 106 var stub = generateDisabledMethodStub(objectName + '.' + propertyName, |
| 92 opt_messageSuffix); | 107 opt_messageSuffix); |
| 93 stub._is_platform_app_disabled_getter = true; | 108 stub._is_platform_app_disabled_getter = true; |
| 94 $Object.defineProperty(object, propertyName, { | 109 $Object.defineProperty(object, propertyName, { |
| 95 configurable: true, | 110 configurable: true, |
| 96 enumerable: false, | 111 enumerable: false, |
| 97 get: stub, | 112 get: stub, |
| 98 set: function(value) { | 113 set: function(value) { |
| 99 var descriptor = $Object.getOwnPropertyDescriptor(this, propertyName); | 114 var descriptor = $Object.getOwnPropertyDescriptor(this, propertyName); |
| 100 if (!descriptor || !descriptor.get || | 115 if (!descriptor || !descriptor.get || |
| (...skipping 22 matching lines...) Expand all Loading... |
| 123 * @param {Object} object The object with properties to disable. The prototype | 138 * @param {Object} object The object with properties to disable. The prototype |
| 124 * is preferred. | 139 * is preferred. |
| 125 * @param {string} objectName The display name to use in the error message | 140 * @param {string} objectName The display name to use in the error message |
| 126 * thrown by the setter stub (this is the name that the object is commonly | 141 * thrown by the setter stub (this is the name that the object is commonly |
| 127 * referred to by web developers, e.g. "document" instead of | 142 * referred to by web developers, e.g. "document" instead of |
| 128 * "HTMLDocument"). | 143 * "HTMLDocument"). |
| 129 * @param {Array<string>} propertyNames names of properties to disable. | 144 * @param {Array<string>} propertyNames names of properties to disable. |
| 130 */ | 145 */ |
| 131 function disableSetters(object, objectName, propertyNames, opt_messageSuffix) { | 146 function disableSetters(object, objectName, propertyNames, opt_messageSuffix) { |
| 132 $Array.forEach(propertyNames, function(propertyName) { | 147 $Array.forEach(propertyNames, function(propertyName) { |
| 148 logging.DCHECK($Object.getOwnPropertyDescriptor(object, propertyName), |
| 149 objectName + ': ' + propertyName); |
| 133 var stub = generateDisabledMethodStub(objectName + '.' + propertyName, | 150 var stub = generateDisabledMethodStub(objectName + '.' + propertyName, |
| 134 opt_messageSuffix); | 151 opt_messageSuffix); |
| 135 $Object.defineProperty(object, propertyName, { | 152 $Object.defineProperty(object, propertyName, { |
| 136 configurable: true, | 153 configurable: false, |
| 137 enumerable: false, | 154 enumerable: false, |
| 138 get: function() { | 155 get: function() { |
| 139 return; | 156 return; |
| 140 }, | 157 }, |
| 141 set: stub | 158 set: stub |
| 142 }); | 159 }); |
| 143 }); | 160 }); |
| 144 } | 161 } |
| 145 | 162 |
| 146 // Disable benign Document methods. | 163 // Disable benign Document methods. |
| 147 disableMethods(HTMLDocument.prototype, 'document', ['open', 'clear', 'close']); | 164 disableMethods(Document.prototype, 'document', ['open', 'close']); |
| 165 disableMethods(HTMLDocument.prototype, 'document', ['clear']); |
| 148 | 166 |
| 149 // Replace evil Document methods with exception-throwing stubs. | 167 // Replace evil Document methods with exception-throwing stubs. |
| 150 disableMethods(HTMLDocument.prototype, 'document', ['write', 'writeln'], true); | 168 disableMethods(Document.prototype, 'document', ['write', 'writeln'], true); |
| 151 | 169 |
| 152 // Disable history. | 170 // Disable history. |
| 153 Object.defineProperty(window, "history", { value: {} }); | 171 Object.defineProperty(window, "history", { value: {} }); |
| 172 // Note: we just blew away the history object, so we need to ignore the fact |
| 173 // that these properties aren't defined on the object. |
| 154 disableGetters(window.history, 'history', | 174 disableGetters(window.history, 'history', |
| 155 ['back', 'forward', 'go', 'length', 'pushState', 'replaceState', 'state']); | 175 ['back', 'forward', 'go', 'length', 'pushState', 'replaceState', 'state'], |
| 176 null, true); |
| 156 | 177 |
| 157 // Disable find. | 178 // Disable find. |
| 158 disableMethods(window, 'window', ['find']); | 179 disableMethods(window, 'window', ['find']); |
| 159 disableMethods(Window.prototype, 'window', ['find']); | |
| 160 | 180 |
| 161 // Disable modal dialogs. Shell windows disable these anyway, but it's nice to | 181 // Disable modal dialogs. Shell windows disable these anyway, but it's nice to |
| 162 // warn. | 182 // warn. |
| 163 disableMethods(window, 'window', ['alert', 'confirm', 'prompt']); | 183 disableMethods(window, 'window', ['alert', 'confirm', 'prompt']); |
| 164 disableMethods(Window.prototype, 'window', ['alert', 'confirm', 'prompt']); | |
| 165 | 184 |
| 166 // Disable window.*bar. | 185 // Disable window.*bar. |
| 167 disableGetters(window, 'window', | 186 disableGetters(window, 'window', |
| 168 ['locationbar', 'menubar', 'personalbar', 'scrollbars', 'statusbar', | 187 ['locationbar', 'menubar', 'personalbar', 'scrollbars', 'statusbar', |
| 169 'toolbar']); | 188 'toolbar']); |
| 170 | 189 |
| 171 // Disable window.localStorage. | 190 // Disable window.localStorage. |
| 172 // Sometimes DOM security policy prevents us from doing this (e.g. for data: | 191 // Sometimes DOM security policy prevents us from doing this (e.g. for data: |
| 173 // URLs) so wrap in try-catch. | 192 // URLs) so wrap in try-catch. |
| 174 try { | 193 try { |
| (...skipping 12 matching lines...) Expand all Loading... |
| 187 if (document.readyState != 'loading') | 206 if (document.readyState != 'loading') |
| 188 return; | 207 return; |
| 189 | 208 |
| 190 // Deprecated document properties from | 209 // Deprecated document properties from |
| 191 // https://developer.mozilla.org/en/DOM/document. | 210 // https://developer.mozilla.org/en/DOM/document. |
| 192 // To deprecate document.all, simply changing its getter and setter would | 211 // To deprecate document.all, simply changing its getter and setter would |
| 193 // activate its cache mechanism, and degrade the performance. Here we assign | 212 // activate its cache mechanism, and degrade the performance. Here we assign |
| 194 // it first to 'undefined' to avoid this. | 213 // it first to 'undefined' to avoid this. |
| 195 document.all = undefined; | 214 document.all = undefined; |
| 196 disableGetters(document, 'document', | 215 disableGetters(document, 'document', |
| 197 ['alinkColor', 'all', 'bgColor', 'fgColor', 'linkColor', 'vlinkColor']); | 216 ['alinkColor', 'all', 'bgColor', 'fgColor', 'linkColor', 'vlinkColor'], |
| 217 null, true); |
| 198 }, true); | 218 }, true); |
| 199 | 219 |
| 200 // Disable onunload, onbeforeunload. | 220 // Disable onunload, onbeforeunload. |
| 201 disableSetters(window, 'window', ['onbeforeunload', 'onunload']); | 221 disableSetters(window, 'window', ['onbeforeunload', 'onunload']); |
| 202 disableSetters(Window.prototype, 'window', ['onbeforeunload', 'onunload']); | |
| 203 var eventTargetAddEventListener = EventTarget.prototype.addEventListener; | 222 var eventTargetAddEventListener = EventTarget.prototype.addEventListener; |
| 204 EventTarget.prototype.addEventListener = function(type) { | 223 EventTarget.prototype.addEventListener = function(type) { |
| 224 var args = $Array.slice(arguments); |
| 225 // Note: Force conversion to a string in order to catch any funny attempts |
| 226 // to pass in something that evals to 'unload' but wouldn't === 'unload'. |
| 227 var type = (args[0] += ''); |
| 205 if (type === 'unload' || type === 'beforeunload') | 228 if (type === 'unload' || type === 'beforeunload') |
| 206 generateDisabledMethodStub(type)(); | 229 generateDisabledMethodStub(type)(); |
| 207 else | 230 else |
| 208 return $Function.apply(eventTargetAddEventListener, this, arguments); | 231 return $Function.apply(eventTargetAddEventListener, this, args); |
| 209 }; | 232 }; |
| OLD | NEW |