#!/usr/bin/env bash # --------------------------------------------------------------------------- # Script : txt2bin - Convert text file to portable Linux binary with stdout # Usage : txt2bin input.txt output_name # Release : 13 Dec 2025 # Update : 12 Aug 2026 - Size-Optimized Binary (from ~16kb to ~5kb) # License : Blue Oak Model License # Copyright: 640kb.neocities.org # A fun little script based on the short story: The Council of Linux Greybeards # https://640kb.neocities.org/short.stories/shorts/the.council.of.linux.greybeards.html # See why this script exists: # https://640kb.neocities.org/apps/apps.free/txt2bin-why.html # --------------------------------------------------------------------------- if [[ "$1" == "-h" || "$1" == "--help" ]]; then echo echo " ---------------------------------------------------------------------------" echo " txt2bin converts text files into self-displaying portable Linux binaries" echo echo " Usage : txt2bin input.txt output_name (.c extension automatically added)" echo echo " Creates : output_name.bin (a portable Linux executable)" echo echo " Examples:" echo " txt2bin infile.txt out.txt # Creates out.txt.bin (via out.txt.c)" echo " txt2bin asciiart.txt art # Creates art.bin (via art.c)" echo " ---------------------------------------------------------------------------" echo " Features:" echo echo " - NEW: Size Optimizations (printf replaced with write(); compiler flags)" echo " - 80x25 input works best" echo " - Falls back to gcc if musl-gcc unavailable" echo " - Prevents accidental overwrites with safety prompts" echo " - Directly replaces \"cat file.txt\" (who wants to type all of that anyway?)" echo " - Keep your deep thoughts safe from malicious edits designed to mock them" echo " - Monetize open standards using a vendor lock-in technique" echo " - Subscriptions & spyware coming soon..." echo " ---------------------------------------------------------------------------" echo exit 0 fi if [ $# -ne 2 ]; then echo echo " Usage: txt2bin input.txt output_name" echo echo " For more information: txt2bin -h" echo exit 1 fi INPUT="$1" OUTPUT_BASE="$2" OUTPUT_C="${OUTPUT_BASE}.c" OUTPUT_BIN="${OUTPUT_BASE}.bin" if [ "$INPUT" = "$OUTPUT_C" ] || [ "$INPUT" = "$OUTPUT_BIN" ]; then echo echo " Error: Input file cannot have the same name as output files" echo " This would overwrite your source file!" echo exit 1 fi if [ -f "$OUTPUT_BIN" ]; then read -p "Warning: $OUTPUT_BIN already exists. Overwrite? (y/N) " -n 1 -r echo if [[ ! $REPLY =~ ^[Yy]$ ]]; then echo " Aborted. Please choose a different output name." exit 1 fi rm -f "$OUTPUT_BIN" fi if [ -f "$OUTPUT_C" ]; then read -p "Warning: $OUTPUT_C already exists. Overwrite? (y/N) " -n 1 -r echo if [[ ! $REPLY =~ ^[Yy]$ ]]; then echo " Aborted. Please choose a different output name." exit 1 fi rm -f "$OUTPUT_C" fi generate_c_source() { echo '#include ' echo '' echo 'int main(void) {' echo ' const char text[] = R"(' cat "$INPUT" echo '' echo ')";' echo ' write(1, text, sizeof(text) - 1);' echo ' return 0;' echo '}' } compile_with_fallback() { local compiler="$1" local flags="$2" local method="$3" echo -n " Compiling with $compiler... " if $compiler $flags -o "$OUTPUT_BIN" "$OUTPUT_C"; then echo echo " Created: $OUTPUT_BIN" echo " Size: $(stat -c%s "$OUTPUT_BIN") bytes" return 0 else echo " Failed" return 1 fi } echo echo " Generating minimal C source (using write() syscall)..." generate_c_source > "$OUTPUT_C" || { echo "Error creating $OUTPUT_C"; exit 1; } echo " Created: $OUTPUT_C" echo SIZE_FLAGS="-Os -s -ffunction-sections -fdata-sections -Wl,--gc-sections -no-pie" if command -v musl-gcc >/dev/null 2>&1; then if ! compile_with_fallback "musl-gcc" "-static $SIZE_FLAGS" "musl static (minimal)"; then echo " musl-gcc failed, trying standard gcc..." if compile_with_fallback "gcc" "-static $SIZE_FLAGS" "glibc static (larger)"; then echo " (Note: glibc static binaries are larger than musl)" fi fi elif compile_with_fallback "gcc" "-static $SIZE_FLAGS" "glibc static (larger)"; then : else echo " Compilation failed: Could not create static binary" echo " Please install musl-tools (for musl-gcc) or build-essential (for gcc)" exit 1 fi echo echo " The Linux portable binary is ready..." echo " Run it as: ./$OUTPUT_BIN" echo