-
-
Save Gamer92000/c39de1a608b7997aab94a4084f92eeae to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// --==-- FFE Test Case Generator --==-- | |
// This script will use all images on the page and assemble them into a test | |
// case. All images will be downloaded 300 times and then zipped up. The | |
// TeamSpeak client imposes several restrictions that complicate this. By | |
// default, it is not possible to load scripts from external sources. This | |
// means that the JSZip library has to be pasted into the console. The | |
// TeamSpeak client also does not allow to download files from the JavaScript | |
// context. This means that the zip file has to be converted to a base64 | |
// string and then printed to the console. This string can then be copied | |
// into a new file and decoded with a base64 decoder. The resulting file | |
// will be a zip file containing all images. However, as the TeamSpeak client | |
// shadows the `console.log` and `console.warn` functions, the output will | |
// be printed to the console using `console.error`. | |
// -=- Libraries -=- | |
// JSZip: https://stuk.github.io/jszip/ -> https://raw.githubusercontent.com/Stuk/jszip/master/dist/jszip.min.js | |
// using more tries would give potentially more diverse results, but crashes due to memory usage | |
let tries = 300; | |
// find all image sources on the page | |
let images = [].slice.call(document.getElementsByTagName("IMG")).map((image) => image.src); | |
// exclude duplicates and non-relevant images | |
images = new Set(images.filter((image) => image.endsWith("ts-frame=1") && image.startsWith("tsic://"))); | |
(async () => { | |
for (image of images) { | |
console.error(image); | |
let zip = new JSZip(); | |
for (let i = 0; i < tries; i++) { | |
await fetch(image, { | |
cache: "no-store", | |
mode: "no-cors" | |
}).then((r) => r.arrayBuffer()).then((j) => { | |
zip.file(`${String(i).padStart(2, '0')}.png`, j); | |
}); | |
} | |
zip.generateAsync({ type: "blob" }) | |
.then((blob) => blob.arrayBuffer()) | |
.then((buffer) => { | |
// convert buffer to base64 string | |
// this can't be done through the spread operator | |
// as the recursion will be too deep and fail | |
let binary = ''; | |
let bytes = new Uint8Array(buffer); | |
let len = bytes.byteLength; | |
for (let i = 0; i < len; i++) { | |
binary += String.fromCharCode(bytes[i]); | |
} | |
let base64Image = window.btoa(binary); | |
console.error(base64Image); | |
}); | |
} | |
})(); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from pathlib import Path | |
def compare_file_content(files: list[Path]): | |
with open(files[0], "rb") as f: | |
data = f.read() | |
for f in files[1:]: | |
with open(f, "rb") as f2: | |
data2 = f2.read() | |
if data != data2: | |
return False | |
return True | |
def check_break_point(files: list[Path], max_size: int): | |
# it's enough to check the first file | |
with open(files[0], "rb") as f: | |
data = f.read() | |
if len(data) % 2**16 != 0: | |
return False | |
if len(data) >= max_size: | |
return False | |
return True | |
for i, image in enumerate(sorted([*Path("./results").iterdir()], key=lambda x: x.name)): | |
print(f"π Analyzing subject: {i+1}") | |
# for each image there are 300 files | |
# some files are broken, most are not | |
# we can distinguish them by their size | |
# so find the most common size | |
sizes = {} | |
for f in image.iterdir(): | |
size = f.stat().st_size | |
if size not in sizes: | |
sizes[size] = 0 | |
sizes[size] += 1 | |
most_common_size = max(sizes, key=lambda x: sizes[x]) | |
# now we can find the broken files | |
broken_files = [] | |
for f in image.iterdir(): | |
if f.stat().st_size != most_common_size: | |
broken_files.append(f) | |
print(f" π Expected size: {most_common_size} bytes") | |
if len(broken_files) == 0: | |
print(" β No broken files") | |
continue | |
print(f" β οΈ Found {len(broken_files) / 300:.2%} broken files ({len(broken_files)}/300)") | |
# group the broken files by their size | |
broken_files_by_size = {} | |
for f in broken_files: | |
size = f.stat().st_size | |
if size not in broken_files_by_size: | |
broken_files_by_size[size] = [] | |
broken_files_by_size[size].append(f) | |
# run checks for each group | |
for size in broken_files_by_size: | |
files = broken_files_by_size[size] | |
print(f" π Checking {len(files)} broken files ({len(files)/300:.2%}) of size {size}") | |
# check if the files are the same | |
if compare_file_content(files): | |
print(f" β All files are the same") | |
else: | |
print(f" β The Files differ in their content") | |
# check if the files are broken at an expected point | |
if check_break_point(files, most_common_size): | |
print(f" β The files are truncated at a multiple of 2^16") | |
continue | |
else: | |
print(f" β The files exhibit an unexpected size") | |
expected_file = None | |
# find a file with the expected size | |
for f in image.iterdir(): | |
if f.stat().st_size == most_common_size: | |
with open(f, "rb") as f2: | |
expected_file = f2.read() | |
break | |
# if the file is larger than the expected size, | |
# compare the expected bytes with the actual bytes | |
# if size > most_common_size: | |
# find the offset up to which the bytes are the same | |
offset = 0 | |
with open(files[0], "rb") as f: | |
data = f.read() | |
while expected_file[offset] == data[offset]: | |
offset += 1 | |
print(f" π The files differ in content at offset {offset} from the expectation") | |
# assume the file ends correctly | |
# find the offset from the end up to which the bytes are the same | |
offset_end = 0 | |
with open(files[0], "rb") as f: | |
data = f.read() | |
while expected_file[-offset_end] == data[-offset_end]: | |
offset_end += 1 | |
# calculate offset from the beginning | |
print(f" π° The unexpected content matches the expectation between offset {len(data) - offset_end} and the end") | |
# if the file is smaller than the expected size, | |
# find the missing bytes | |
if size < most_common_size: | |
print(f" π₯ The files are missing {most_common_size - offset - offset_end + 1} bytes in the middle") | |
# if the file is larger than the expected size, | |
# find the extra bytes | |
if size > most_common_size: | |
if data[offset:-offset_end] == expected_file[offset-2^16:-offset_end-2^16]: | |
print(f" π₯ The files have {size - most_common_size} duplicate bytes in the middle") | |
else: | |
print(f" π₯ The files have {size - most_common_size} extra bytes in the middle") |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment