]> git.jsancho.org Git - lugaru.git/blob - Misc/fix-hardcoded-hex-paths.sh
Bump version to 1.3-dev
[lugaru.git] / Misc / fix-hardcoded-hex-paths.sh
1 #!/bin/bash
2
3 ### Description
4 #
5 # This script replaces broken hardcoded strings in binary files (e.g. maps)
6 # with another string given by the user.
7 #
8 # The input and ouput strings are given by the file passed as first argument,
9 # which should be of the form:
10 #
11 # old string<TAB>new string
12 # other old string<TAB>other new string
13 # etc.
14 #
15 # The strings are fixed by binary replacements of their hex code. The hex
16 # representation of a string starts with its length on four bytes, but in
17 # this script we currently only fix the fourth byte (the others are typically
18 # null), which means we support strings up to 255 chars.
19 #
20 # The binary files to fix are passed as second and optionally more arguments.
21 #
22
23 ### Usage
24 #
25 # ./Misc/fix-hardcoded-hex-paths.sh [file describing fixes] [maps to fix]
26 #
27 # e.g.:
28 #
29 # ./Misc/fix-hardcoded-hex-paths.sh Misc/list-hardcoded-paths-fixes.txt Data/Maps/jendraz*
30 #
31
32 ### Functions
33
34 ascii2hex () {
35     local len=$(echo -n $1 | wc -c)
36     if [ $len -gt 255 ]; then echo "This poor script can't handle such long strings. Blame Akien."; exit 1; fi
37     len='\x'$(printf '%02x\n' $len)
38     local hexstring=$(echo -n $1 | xxd -ps | sed 's/[[:xdigit:]]\{2\}/\\x&/g')
39     # Seems xxd will put some separators on long strings
40     return=$len$(echo $hexstring | sed 's/ //g')
41     return
42 }
43
44 hex2ascii () {
45     local string=$(echo -n $1 | cut -c 4-)
46     return=$(echo $string | sed 's/\x//g' | xxd -r -ps)
47     return
48 }
49
50 ### Script
51
52 in_file="$1"
53 target_files="${@:2}"
54
55 if [ ! -e $in_file ]; then echo "You must pass a valid filename as argument, got $in_file."; exit 1; fi
56
57 if [ -z "${target_files}" ]; then echo "You muss pass a list of files as second argument."; exit 1; fi
58
59 echo -e "Replacing hardcoded strings as listed in $in_file in the following files:\n\n$target_files\n"
60
61 while IFS='' read -r line || [[ -n "$line" ]]; do
62     input=$(echo "$line" | cut -f1)
63     output=$(echo "$line" | cut -f2)
64     echo "Replacing '${input}' by '${output}'."
65
66     ascii2hex "$input"
67     in_hex=$return
68     hex2ascii "$in_hex"
69     if [ "$return" != "$input" ]; then echo "Something went wrong in the conversion of $input back and forth to hex."; fi
70
71     ascii2hex "$output"
72     out_hex=$return
73     hex2ascii "$out_hex"
74     if [ "$return" != "$output" ]; then echo "Something went wrong in the conversion of $output back and forth to hex."; fi
75
76     for target_file in $target_files; do
77         sed -i 's/'${in_hex}'/'${out_hex}'/g' "${target_file}"
78     done
79 done < "$in_file"