arkenfox / TZP

TorZillaPrint: Firefox & Tor Browser fingerprint testing
https://arkenfox.github.io/TZP
MIT License
194 stars 27 forks source link

htmlelement keys is not stable between TZP vs CREEPY #267

Open Thorin-Oakenpants opened 9 months ago

Thorin-Oakenpants commented 9 months ago

@abrahamjuliot .. what's going on here?

TZP code

    const id = "html-element-version"
    const element = document.createElement("div")
    element.setAttribute("id", id)
    document.body.appendChild(element)
    const htmlElement = document.getElementById(id)
    const keys = []
    for (const key in htmlElement) {keys.push(key)}
    //... etc .. using same mini hashing function as creepy
    try {document.getElementById(id).remove()} catch(e) {} // cleanup

on creepy I get 312 keys hash b2a71fab on TZP I get 312 keys hash 43c289ca

so I compared them

// CRP b2a71fab
let aCRP = ['version','click','attachInternals','showPopover','hidePopover','togglePopover','focus','blur','title','lang','translate','dir','innerText','outerText','hidden','inert','accessKey','accessKeyLabel','draggable','contentEditable','isContentEditable','popover','spellcheck','inputMode','enterKeyHint','autocapitalize','nonce','offsetParent','offsetTop','offsetLeft','offsetWidth','offsetHeight','style','onabort','onblur','onfocus','oncancel','onauxclick','onbeforeinput','onbeforetoggle','oncanplay','oncanplaythrough','onchange','onclick','onclose','oncontextmenu','oncopy','oncuechange','oncut','ondblclick','ondrag','ondragend','ondragenter','ondragleave','ondragover','ondragstart','ondrop','ondurationchange','onemptied','onended','onformdata','oninput','oninvalid','onkeydown','onkeypress','onkeyup','onload','onloadeddata','onloadedmetadata','onloadstart','onmousedown','onmouseenter','onmouseleave','onmousemove','onmouseout','onmouseover','onmouseup','onwheel','onpaste','onpause','onplay','onplaying','onprogress','onratechange','onreset','onresize','onscroll','onscrollend','onsecuritypolicyviolation','onseeked','onseeking','onselect','onslotchange','onstalled','onsubmit','onsuspend','ontimeupdate','onvolumechange','onwaiting','onselectstart','onselectionchange','ontoggle','onpointercancel','onpointerdown','onpointerup','onpointermove','onpointerout','onpointerover','onpointerenter','onpointerleave','ongotpointercapture','onlostpointercapture','onmozfullscreenchange','onmozfullscreenerror','onanimationcancel','onanimationend','onanimationiteration','onanimationstart','ontransitioncancel','ontransitionend','ontransitionrun','ontransitionstart','onwebkitanimationend','onwebkitanimationiteration','onwebkitanimationstart','onwebkittransitionend','dataset','autofocus','tabIndex','onerror','getAttributeNames','getAttribute','getAttributeNS','toggleAttribute','setAttribute','setAttributeNS','removeAttribute','removeAttributeNS','hasAttribute','hasAttributeNS','hasAttributes','closest','matches','webkitMatchesSelector','getElementsByTagName','getElementsByTagNameNS','getElementsByClassName','insertAdjacentElement','insertAdjacentText','mozMatchesSelector','setPointerCapture','releasePointerCapture','hasPointerCapture','setCapture','releaseCapture','getAttributeNode','setAttributeNode','removeAttributeNode','getAttributeNodeNS','setAttributeNodeNS','getClientRects','getBoundingClientRect','checkVisibility','scrollIntoView','scroll','scrollTo','scrollBy','insertAdjacentHTML','querySelector','querySelectorAll','attachShadow','requestFullscreen','mozRequestFullScreen','requestPointerLock','setHTMLUnsafe','animate','getAnimations','before','after','replaceWith','remove','getBoxQuads','convertQuadFromNode','convertRectFromNode','convertPointFromNode','prepend','append','replaceChildren','namespaceURI','prefix','localName','tagName','id','className','classList','part','attributes','scrollTop','scrollLeft','scrollWidth','scrollHeight','clientTop','clientLeft','clientWidth','clientHeight','scrollTopMax','scrollLeftMax','innerHTML','outerHTML','shadowRoot','assignedSlot','slot','onfullscreenchange','onfullscreenerror','role','ariaAtomic','ariaAutoComplete','ariaBusy','ariaChecked','ariaColCount','ariaColIndex','ariaColIndexText','ariaColSpan','ariaCurrent','ariaDescription','ariaDisabled','ariaExpanded','ariaHasPopup','ariaHidden','ariaInvalid','ariaKeyShortcuts','ariaLabel','ariaLevel','ariaLive','ariaModal','ariaMultiLine','ariaMultiSelectable','ariaOrientation','ariaPlaceholder','ariaPosInSet','ariaPressed','ariaReadOnly','ariaRelevant','ariaRequired','ariaRoleDescription','ariaRowCount','ariaRowIndex','ariaRowIndexText','ariaRowSpan','ariaSelected','ariaSetSize','ariaSort','ariaValueMax','ariaValueMin','ariaValueNow','ariaValueText','previousElementSibling','nextElementSibling','children','firstElementChild','lastElementChild','childElementCount','getRootNode','hasChildNodes','insertBefore','appendChild','replaceChild','removeChild','normalize','cloneNode','isSameNode','isEqualNode','compareDocumentPosition','contains','lookupPrefix','lookupNamespaceURI','isDefaultNamespace','nodeType','nodeName','baseURI','isConnected','ownerDocument','parentNode','parentElement','childNodes','firstChild','lastChild','previousSibling','nextSibling','nodeValue','textContent','ELEMENT_NODE','ATTRIBUTE_NODE','TEXT_NODE','CDATA_SECTION_NODE','ENTITY_REFERENCE_NODE','ENTITY_NODE','PROCESSING_INSTRUCTION_NODE','COMMENT_NODE','DOCUMENT_NODE','DOCUMENT_TYPE_NODE','DOCUMENT_FRAGMENT_NODE','NOTATION_NODE','DOCUMENT_POSITION_DISCONNECTED','DOCUMENT_POSITION_PRECEDING','DOCUMENT_POSITION_FOLLOWING','DOCUMENT_POSITION_CONTAINS','DOCUMENT_POSITION_CONTAINED_BY','DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC','addEventListener','removeEventListener','dispatchEvent']
// TZP 43c289ca
let aTZP = ['align','click','attachInternals','showPopover','hidePopover','togglePopover','focus','blur','title','lang','translate','dir','innerText','outerText','hidden','inert','accessKey','accessKeyLabel','draggable','contentEditable','isContentEditable','popover','spellcheck','inputMode','enterKeyHint','autocapitalize','nonce','offsetParent','offsetTop','offsetLeft','offsetWidth','offsetHeight','style','onabort','onblur','onfocus','oncancel','onauxclick','onbeforeinput','onbeforetoggle','oncanplay','oncanplaythrough','onchange','onclick','onclose','oncontextmenu','oncopy','oncuechange','oncut','ondblclick','ondrag','ondragend','ondragenter','ondragleave','ondragover','ondragstart','ondrop','ondurationchange','onemptied','onended','onformdata','oninput','oninvalid','onkeydown','onkeypress','onkeyup','onload','onloadeddata','onloadedmetadata','onloadstart','onmousedown','onmouseenter','onmouseleave','onmousemove','onmouseout','onmouseover','onmouseup','onwheel','onpaste','onpause','onplay','onplaying','onprogress','onratechange','onreset','onresize','onscroll','onscrollend','onsecuritypolicyviolation','onseeked','onseeking','onselect','onslotchange','onstalled','onsubmit','onsuspend','ontimeupdate','onvolumechange','onwaiting','onselectstart','onselectionchange','ontoggle','onpointercancel','onpointerdown','onpointerup','onpointermove','onpointerout','onpointerover','onpointerenter','onpointerleave','ongotpointercapture','onlostpointercapture','onmozfullscreenchange','onmozfullscreenerror','onanimationcancel','onanimationend','onanimationiteration','onanimationstart','ontransitioncancel','ontransitionend','ontransitionrun','ontransitionstart','onwebkitanimationend','onwebkitanimationiteration','onwebkitanimationstart','onwebkittransitionend','dataset','autofocus','tabIndex','onerror','getAttributeNames','getAttribute','getAttributeNS','toggleAttribute','setAttribute','setAttributeNS','removeAttribute','removeAttributeNS','hasAttribute','hasAttributeNS','hasAttributes','closest','matches','webkitMatchesSelector','getElementsByTagName','getElementsByTagNameNS','getElementsByClassName','insertAdjacentElement','insertAdjacentText','mozMatchesSelector','setPointerCapture','releasePointerCapture','hasPointerCapture','setCapture','releaseCapture','getAttributeNode','setAttributeNode','removeAttributeNode','getAttributeNodeNS','setAttributeNodeNS','getClientRects','getBoundingClientRect','checkVisibility','scrollIntoView','scroll','scrollTo','scrollBy','insertAdjacentHTML','querySelector','querySelectorAll','attachShadow','requestFullscreen','mozRequestFullScreen','requestPointerLock','setHTMLUnsafe','animate','getAnimations','before','after','replaceWith','remove','getBoxQuads','convertQuadFromNode','convertRectFromNode','convertPointFromNode','prepend','append','replaceChildren','namespaceURI','prefix','localName','tagName','id','className','classList','part','attributes','scrollTop','scrollLeft','scrollWidth','scrollHeight','clientTop','clientLeft','clientWidth','clientHeight','scrollTopMax','scrollLeftMax','innerHTML','outerHTML','shadowRoot','assignedSlot','slot','onfullscreenchange','onfullscreenerror','role','ariaAtomic','ariaAutoComplete','ariaBusy','ariaChecked','ariaColCount','ariaColIndex','ariaColIndexText','ariaColSpan','ariaCurrent','ariaDescription','ariaDisabled','ariaExpanded','ariaHasPopup','ariaHidden','ariaInvalid','ariaKeyShortcuts','ariaLabel','ariaLevel','ariaLive','ariaModal','ariaMultiLine','ariaMultiSelectable','ariaOrientation','ariaPlaceholder','ariaPosInSet','ariaPressed','ariaReadOnly','ariaRelevant','ariaRequired','ariaRoleDescription','ariaRowCount','ariaRowIndex','ariaRowIndexText','ariaRowSpan','ariaSelected','ariaSetSize','ariaSort','ariaValueMax','ariaValueMin','ariaValueNow','ariaValueText','previousElementSibling','nextElementSibling','children','firstElementChild','lastElementChild','childElementCount','getRootNode','hasChildNodes','insertBefore','appendChild','replaceChild','removeChild','normalize','cloneNode','isSameNode','isEqualNode','compareDocumentPosition','contains','lookupPrefix','lookupNamespaceURI','isDefaultNamespace','nodeType','nodeName','baseURI','isConnected','ownerDocument','parentNode','parentElement','childNodes','firstChild','lastChild','previousSibling','nextSibling','nodeValue','textContent','ELEMENT_NODE','ATTRIBUTE_NODE','TEXT_NODE','CDATA_SECTION_NODE','ENTITY_REFERENCE_NODE','ENTITY_NODE','PROCESSING_INSTRUCTION_NODE','COMMENT_NODE','DOCUMENT_NODE','DOCUMENT_TYPE_NODE','DOCUMENT_FRAGMENT_NODE','NOTATION_NODE','DOCUMENT_POSITION_DISCONNECTED','DOCUMENT_POSITION_PRECEDING','DOCUMENT_POSITION_FOLLOWING','DOCUMENT_POSITION_CONTAINS','DOCUMENT_POSITION_CONTAINED_BY','DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC','addEventListener','removeEventListener','dispatchEvent']

let onlyTZP = aTZP.filter(x => !aCRP.includes(x))
let onlyCRP = aCRP.filter(x => !aTZP.includes(x))
let aCommon = aCRP.filter(x => aTZP.includes(x))
console.log("onlyTZP", onlyTZP.length+"\n", "['"+ onlyTZP.join("','") +"']" )
console.log("onlyCRP", onlyCRP.length+"\n", "['"+ onlyCRP.join("','") +"']" )
console.log("aCommon", aCommon.length+"\n", "['"+ aCommon.join("','") +"']" )

results

onlyTZP 1
 ['align']

onlyCRP 1
 ['version']

aCommon 311
 ['click','attachInternals','showPopover','hidePopover','togglePopover','focus','blur','title','lang','translate','dir','innerText','outerText','hidden','inert','accessKey','accessKeyLabel','draggable','contentEditable','isContentEditable','popover','spellcheck','inputMode','enterKeyHint','autocapitalize','nonce','offsetParent','offsetTop','offsetLeft','offsetWidth','offsetHeight','style','onabort','onblur','onfocus','oncancel','onauxclick','onbeforeinput','onbeforetoggle','oncanplay','oncanplaythrough','onchange','onclick','onclose','oncontextmenu','oncopy','oncuechange','oncut','ondblclick','ondrag','ondragend','ondragenter','ondragleave','ondragover','ondragstart','ondrop','ondurationchange','onemptied','onended','onformdata','oninput','oninvalid','onkeydown','onkeypress','onkeyup','onload','onloadeddata','onloadedmetadata','onloadstart','onmousedown','onmouseenter','onmouseleave','onmousemove','onmouseout','onmouseover','onmouseup','onwheel','onpaste','onpause','onplay','onplaying','onprogress','onratechange','onreset','onresize','onscroll','onscrollend','onsecuritypolicyviolation','onseeked','onseeking','onselect','onslotchange','onstalled','onsubmit','onsuspend','ontimeupdate','onvolumechange','onwaiting','onselectstart','onselectionchange','ontoggle','onpointercancel','onpointerdown','onpointerup','onpointermove','onpointerout','onpointerover','onpointerenter','onpointerleave','ongotpointercapture','onlostpointercapture','onmozfullscreenchange','onmozfullscreenerror','onanimationcancel','onanimationend','onanimationiteration','onanimationstart','ontransitioncancel','ontransitionend','ontransitionrun','ontransitionstart','onwebkitanimationend','onwebkitanimationiteration','onwebkitanimationstart','onwebkittransitionend','dataset','autofocus','tabIndex','onerror','getAttributeNames','getAttribute','getAttributeNS','toggleAttribute','setAttribute','setAttributeNS','removeAttribute','removeAttributeNS','hasAttribute','hasAttributeNS','hasAttributes','closest','matches','webkitMatchesSelector','getElementsByTagName','getElementsByTagNameNS','getElementsByClassName','insertAdjacentElement','insertAdjacentText','mozMatchesSelector','setPointerCapture','releasePointerCapture','hasPointerCapture','setCapture','releaseCapture','getAttributeNode','setAttributeNode','removeAttributeNode','getAttributeNodeNS','setAttributeNodeNS','getClientRects','getBoundingClientRect','checkVisibility','scrollIntoView','scroll','scrollTo','scrollBy','insertAdjacentHTML','querySelector','querySelectorAll','attachShadow','requestFullscreen','mozRequestFullScreen','requestPointerLock','setHTMLUnsafe','animate','getAnimations','before','after','replaceWith','remove','getBoxQuads','convertQuadFromNode','convertRectFromNode','convertPointFromNode','prepend','append','replaceChildren','namespaceURI','prefix','localName','tagName','id','className','classList','part','attributes','scrollTop','scrollLeft','scrollWidth','scrollHeight','clientTop','clientLeft','clientWidth','clientHeight','scrollTopMax','scrollLeftMax','innerHTML','outerHTML','shadowRoot','assignedSlot','slot','onfullscreenchange','onfullscreenerror','role','ariaAtomic','ariaAutoComplete','ariaBusy','ariaChecked','ariaColCount','ariaColIndex','ariaColIndexText','ariaColSpan','ariaCurrent','ariaDescription','ariaDisabled','ariaExpanded','ariaHasPopup','ariaHidden','ariaInvalid','ariaKeyShortcuts','ariaLabel','ariaLevel','ariaLive','ariaModal','ariaMultiLine','ariaMultiSelectable','ariaOrientation','ariaPlaceholder','ariaPosInSet','ariaPressed','ariaReadOnly','ariaRelevant','ariaRequired','ariaRoleDescription','ariaRowCount','ariaRowIndex','ariaRowIndexText','ariaRowSpan','ariaSelected','ariaSetSize','ariaSort','ariaValueMax','ariaValueMin','ariaValueNow','ariaValueText','previousElementSibling','nextElementSibling','children','firstElementChild','lastElementChild','childElementCount','getRootNode','hasChildNodes','insertBefore','appendChild','replaceChild','removeChild','normalize','cloneNode','isSameNode','isEqualNode','compareDocumentPosition','contains','lookupPrefix','lookupNamespaceURI','isDefaultNamespace','nodeType','nodeName','baseURI','isConnected','ownerDocument','parentNode','parentElement','childNodes','firstChild','lastChild','previousSibling','nextSibling','nodeValue','textContent','ELEMENT_NODE','ATTRIBUTE_NODE','TEXT_NODE','CDATA_SECTION_NODE','ENTITY_REFERENCE_NODE','ENTITY_NODE','PROCESSING_INSTRUCTION_NODE','COMMENT_NODE','DOCUMENT_NODE','DOCUMENT_TYPE_NODE','DOCUMENT_FRAGMENT_NODE','NOTATION_NODE','DOCUMENT_POSITION_DISCONNECTED','DOCUMENT_POSITION_PRECEDING','DOCUMENT_POSITION_FOLLOWING','DOCUMENT_POSITION_CONTAINS','DOCUMENT_POSITION_CONTAINED_BY','DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC','addEventListener','removeEventListener','dispatchEvent']

So why does TZP's first item = align and creepy's = version

please explain yourself, young man! :)

Thorin-Oakenpants commented 9 months ago

I thought maybe something in TZP mountain of html/css/js was causing it, but nope - here's a standalone test (using my code which came from you)

<html><body>
<br>HASH<br><div id="hash"></div><br>DATA<br><div id="data"></div>
<script>
'use strict';
function mini(str) {
    // https://stackoverflow.com/a/22429679
    const json = `${JSON.stringify(str)}`
    let i, len, hash = 0x811c9dc5
    for (i = 0, len = json.length; i < len; i++) {
        hash = Math.imul(31, hash) + json.charCodeAt(i) | 0
    }
    return ('0000000' + (hash >>> 0).toString(16)).slice(-8)
}
try {
    const id = "html-element-version"
    const element = document.createElement("div")
    element.setAttribute("id", id)
    document.body.appendChild(element)
    const htmlElement = document.getElementById(id)
    const keys = []
    for (const key in htmlElement) {keys.push(key)}
    try {document.getElementById(id).remove()} catch(e) {}
    let hash = mini(keys) // 18527130
    document.getElementById("hash").innerHTML = hash +" [" + keys.length +"]"
    document.getElementById("data").innerHTML = "['"+ keys.join("', '") +"']"
} catch (e) {
    document.getElementById("hash").innerHTML = e+""
}
</script></body></html>

here's the result

standalone

Thorin-Oakenpants commented 9 months ago

the only place version shows up is in html

7a1ee797 [312]: html
['version', 'click', 'attachInternals', 'showPopover', 'hidePopover', 'togglePopover', 'focus', 'blur', 'title', 'lang', 'translate', 'dir', 'innerText', 'outerText', 'hidden', 'inert', 'accessKey', 'accessKeyLabel', 'draggable', 'contentEditable', 'isContentEditable', 'popover', 'spellcheck', 'inputMode', 'enterKeyHint', 'autocapitalize', 'nonce', 'offsetParent', 'offsetTop', 'offsetLeft', 'offsetWidth', 'offsetHeight', 'style', 'onabort', 'onblur', 'onfocus', 'oncancel', 'onauxclick', 'onbeforeinput', 'onbeforetoggle', 'oncanplay', 'oncanplaythrough', 'onchange', 'onclick', 'onclose', 'oncontextmenu', 'oncopy', 'oncuechange', 'oncut', 'ondblclick', 'ondrag', 'ondragend', 'ondragenter', 'ondragleave', 'ondragover', 'ondragstart', 'ondrop', 'ondurationchange', 'onemptied', 'onended', 'onformdata', 'oninput', 'oninvalid', 'onkeydown', 'onkeypress', 'onkeyup', 'onload', 'onloadeddata', 'onloadedmetadata', 'onloadstart', 'onmousedown', 'onmouseenter', 'onmouseleave', 'onmousemove', 'onmouseout', 'onmouseover', 'onmouseup', 'onwheel', 'onpaste', 'onpause', 'onplay', 'onplaying', 'onprogress', 'onratechange', 'onreset', 'onresize', 'onscroll', 'onscrollend', 'onsecuritypolicyviolation', 'onseeked', 'onseeking', 'onselect', 'onslotchange', 'onstalled', 'onsubmit', 'onsuspend', 'ontimeupdate', 'onvolumechange', 'onwaiting', 'onselectstart', 'onselectionchange', 'ontoggle', 'onpointercancel', 'onpointerdown', 'onpointerup', 'onpointermove', 'onpointerout', 'onpointerover', 'onpointerenter', 'onpointerleave', 'ongotpointercapture', 'onlostpointercapture', 'onmozfullscreenchange', 'onmozfullscreenerror', 'onanimationcancel', 'onanimationend', 'onanimationiteration', 'onanimationstart', 'ontransitioncancel', 'ontransitionend', 'ontransitionrun', 'ontransitionstart', 'onwebkitanimationend', 'onwebkitanimationiteration', 'onwebkitanimationstart', 'onwebkittransitionend', 'dataset', 'autofocus', 'tabIndex', 'onerror', 'getAttributeNames', 'getAttribute', 'getAttributeNS', 'toggleAttribute', 'setAttribute', 'setAttributeNS', 'removeAttribute', 'removeAttributeNS', 'hasAttribute', 'hasAttributeNS', 'hasAttributes', 'closest', 'matches', 'webkitMatchesSelector', 'getElementsByTagName', 'getElementsByTagNameNS', 'getElementsByClassName', 'insertAdjacentElement', 'insertAdjacentText', 'mozMatchesSelector', 'setPointerCapture', 'releasePointerCapture', 'hasPointerCapture', 'setCapture', 'releaseCapture', 'getAttributeNode', 'setAttributeNode', 'removeAttributeNode', 'getAttributeNodeNS', 'setAttributeNodeNS', 'getClientRects', 'getBoundingClientRect', 'checkVisibility', 'scrollIntoView', 'scroll', 'scrollTo', 'scrollBy', 'insertAdjacentHTML', 'querySelector', 'querySelectorAll', 'attachShadow', 'requestFullscreen', 'mozRequestFullScreen', 'requestPointerLock', 'setHTMLUnsafe', 'animate', 'getAnimations', 'before', 'after', 'replaceWith', 'remove', 'getBoxQuads', 'convertQuadFromNode', 'convertRectFromNode', 'convertPointFromNode', 'prepend', 'append', 'replaceChildren', 'namespaceURI', 'prefix', 'localName', 'tagName', 'id', 'className', 'classList', 'part', 'attributes', 'scrollTop', 'scrollLeft', 'scrollWidth', 'scrollHeight', 'clientTop', 'clientLeft', 'clientWidth', 'clientHeight', 'scrollTopMax', 'scrollLeftMax', 'innerHTML', 'outerHTML', 'shadowRoot', 'assignedSlot', 'slot', 'onfullscreenchange', 'onfullscreenerror', 'role', 'ariaAtomic', 'ariaAutoComplete', 'ariaBusy', 'ariaChecked', 'ariaColCount', 'ariaColIndex', 'ariaColIndexText', 'ariaColSpan', 'ariaCurrent', 'ariaDescription', 'ariaDisabled', 'ariaExpanded', 'ariaHasPopup', 'ariaHidden', 'ariaInvalid', 'ariaKeyShortcuts', 'ariaLabel', 'ariaLevel', 'ariaLive', 'ariaModal', 'ariaMultiLine', 'ariaMultiSelectable', 'ariaOrientation', 'ariaPlaceholder', 'ariaPosInSet', 'ariaPressed', 'ariaReadOnly', 'ariaRelevant', 'ariaRequired', 'ariaRoleDescription', 'ariaRowCount', 'ariaRowIndex', 'ariaRowIndexText', 'ariaRowSpan', 'ariaSelected', 'ariaSetSize', 'ariaSort', 'ariaValueMax', 'ariaValueMin', 'ariaValueNow', 'ariaValueText', 'previousElementSibling', 'nextElementSibling', 'children', 'firstElementChild', 'lastElementChild', 'childElementCount', 'getRootNode', 'hasChildNodes', 'insertBefore', 'appendChild', 'replaceChild', 'removeChild', 'normalize', 'cloneNode', 'isSameNode', 'isEqualNode', 'compareDocumentPosition', 'contains', 'lookupPrefix', 'lookupNamespaceURI', 'isDefaultNamespace', 'nodeType', 'nodeName', 'baseURI', 'isConnected', 'ownerDocument', 'parentNode', 'parentElement', 'childNodes', 'firstChild', 'lastChild', 'previousSibling', 'nextSibling', 'nodeValue', 'textContent', 'ELEMENT_NODE', 'ATTRIBUTE_NODE', 'TEXT_NODE', 'CDATA_SECTION_NODE', 'ENTITY_REFERENCE_NODE', 'ENTITY_NODE', 'PROCESSING_INSTRUCTION_NODE', 'COMMENT_NODE', 'DOCUMENT_NODE', 'DOCUMENT_TYPE_NODE', 'DOCUMENT_FRAGMENT_NODE', 'NOTATION_NODE', 'DOCUMENT_POSITION_DISCONNECTED', 'DOCUMENT_POSITION_PRECEDING', 'DOCUMENT_POSITION_FOLLOWING', 'DOCUMENT_POSITION_CONTAINS', 'DOCUMENT_POSITION_CONTAINED_BY', 'DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC', 'addEventListener', 'removeEventListener', 'dispatchEvent']

if I compare div and html

div [312] 43c289ca
div only 1
['align']

html [312] 7a1ee797
html only 1
['version']

both [311] b1cd1557

just your hash is different - so I can only surmise you are not testing a div but an html .. and you are hashing a different thing - I hash the entire object = e.g. mini(array) - IDK what you are doing

abrahamjuliot commented 9 months ago

I use HTML. It's a little faster if we grab the live element.

const keys = []
for (const key in document.documentElement) keys.push(key)
Thorin-Oakenpants commented 9 months ago

ahhh so that explains it

anyway, live test to be added ... elementkeys.html

1

The interesting things about these is that almost all of them have a massive chunk of values the same and in the same order. In gecko this seems to be everything after click - blink is similar with common lastXitems hashes (I will change this to be post click or whatever per engine)

2

so if you look at the image above which gecko, they are all the same from click on except select which has the value remove before click

so we could actually enumerate every element and reduce the noise and record like such

data_common {
 b1cd1557: [array of 312 items],
 f5bf2f92: [array of 311 items], // as an example, the has is actually something else
},
data {
hr: ["align","color","noShade","size","width", "b1cd1557"] // <- i.e 5 items + data_common.b1cd1557
option: ["disabled",​​​​"form",​​​​"label",​​​​"defaultSelected",​​​​"selected",​​​​"value",​​​​"text",​​​​"index","b1cd1557"]
meter: ["value"."min"."max"."low"."high"."optimum"."labels", "b1cd1557"],
select: [ "item","namedItem","add","remove", .... "f5bf2f92"] // <-- select is slightly different has data_common.f5bf2f92
​​​​}

This then comprehensively covers everything

Once I finish this PoC, I will check stability over time, because the common shit we only need once, but the others may not be worth while collecting if they're super stable and haven't changed e.g. since FF115 (TZP is only concerned with ESR+)

Thorin-Oakenpants commented 9 months ago

like this

3

Thorin-Oakenpants commented 9 months ago

here you go

it also detects fake properties (if they have a space in them,. e.g. no script) - the word to split the contents into common is different in blink - yet to test safari

Thorin-Oakenpants commented 9 months ago

note: NS lies the same across all elements - and the same probably goes for most extensions e.g. JShelter (I need to test more but lack a profile dedicated to it just yet). So detecting some BS entropy is most likely covered by any one of those elements

I think what I will do here is see what ones are super stable in gecko and across OSes and drop them for TZP - and focus on a smaller set - e.g. it would be nice to drop select as it has it's own "common" list after click (and thus adds another 300+ array to the FP when the only diff is one item)

Thorin-Oakenpants commented 6 months ago

I use HTML. It's a little faster if we grab the live element.

it's even faster to use DOMParser