Skip to content

Commit c992043

Browse files
authored
Merge pull request #4 from EKibort/master
Added automatic calculation of parameters and bit another implementation of PRG-VER calculation
2 parents d9bd217 + 98f1fcb commit c992043

11 files changed

Lines changed: 323 additions & 10 deletions

File tree

.github/workflows/c-cpp.yml

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
name: C/C++ CI
2+
3+
on:
4+
push:
5+
branches: [ "master" ]
6+
pull_request:
7+
branches: [ "master" ]
8+
9+
jobs:
10+
build:
11+
12+
runs-on: windows-latest
13+
14+
steps:
15+
- uses: actions/checkout@v3
16+
17+
- name: Cmake
18+
run: |
19+
mkdir build
20+
cd build
21+
cmake ..
22+
cmake --build . --config Release
23+
24+
- uses: actions/upload-artifact@v3
25+
with:
26+
name: release
27+
path: build/Release/
28+
29+

.gitignore

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
.vs/
2+
CMakeSettings.json
3+
build/
4+
out/

CMakeLists.txt

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
cmake_minimum_required (VERSION 3.12)
2+
3+
project ("rz09")
4+
add_executable (parsedat "parsedat.c")
5+
add_executable (translate "translate.c")
6+
add_executable (patchver "patchver.c")

README.md

Lines changed: 35 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -15,11 +15,16 @@ Fields: `<address>` `<lengh>` `<original string>`
1515

1616
Output file is in UCS-2 LE encoding, use Notepad++ (or other UCS-2 LE compatible editor, Chrome is OK for view strings) to see/edit results.
1717

18-
### parsed104_with_addr.txt
19-
Example of parsed initDB.dat (ver.1.04 of AVIC-RZ09).
20-
2118
## translate.c
2219

20+
Usage:
21+
22+
NOTE: You don't need to do any modification in the code, all parameters like versions and offsets will be preserved well.
23+
24+
Also, all parameters can be overwritten via command line parameters
25+
translate <InitDB file name> <Output InitDB file name> <translation file name>
26+
the file names by defualt `initDB.dat`, `initDB_out.dat`, `translation.txt`
27+
2328
### Step 1:
2429
Load strings to translate from `translation.txt` file (in UCS-2 LE encoding):
2530
Fields: `<lenght>` `<original string>` `<translated string>` with TAB delimiter.
@@ -32,18 +37,38 @@ Open source file `initDB.dat`, search and compare source strings and size, and i
3237
Other data blocks copied from source file to output file as-is.
3338
Write results to `initDB_out.dat` file.
3439

40+
all parameters can be owerwrited via commnd line paramters
41+
translate <InitDB file name> <Output InitDB file name> <translation file name>
42+
43+
44+
3545
### translation.txt
36-
File with some strings translated from Japanese to English.
46+
File with some strings translated from Japanese to English. (from 4pda [https://4pda.to/forum/index.php?showtopic=847671&st=320#entry113039189] )
3747

38-
### parsed104_tr_all.txt
39-
File with all Japanese strings, extracted from `initDB.dat`, translated by Google Translator and saved "as-is".
4048

41-
## makever.c
42-
Compile patched .NB0 file to AVIC-compatible FW file.
49+
## patchver.c
50+
Compile patched .NB0 file to AVIC-compatible FW file and modifiy VER and PRG files.
4351

44-
Input:
45-
`fw_104.nb0` - pathced .NB0 file.
52+
Usage:
53+
patchver [PS140PLT.PRG] [PS140PLT.VER] [output.nb0]
4654

4755
Output:
4856
`PS140PLT.PRG` - patched AVIC-platform file.
4957
`PS140PLT.VER` - AVIC-platform version file.
58+
59+
# Whole process of translation
60+
61+
1. Extract existing firmware from Pioneer AVIC-RZ09 from the system menu to SD-card
62+
2. Remove first 0x200 bytes from PS140PLT.PRG by https://sourceforge.net/projects/swissfileknife/files/1-swissfileknife/1.9.8.2/]
63+
`sfk198.exe partcopy PS140PLT.PRG -allfrom 0x200 output.nb0 -yes`
64+
3. Extract `initDB.dat` and use `BinMody` or `dumpromx.exe`
65+
4. translate `initDB.dat` by `translate.exe`
66+
`translate.exe initDB.dat initDB_out.dat translation.txt`
67+
5. Patch `PS140PLT.PRG' and 'PS140PLT.VER' use `patchver.exe`
68+
'patchver.exe PS140PLT.PRG PS140PLT.VER initDB_out.dat'
69+
6. Replace files `PS140PLT.PRG' and 'PS140PLT.VER' on SD-card
70+
7. Upload new firmware to AVIC-RZ09 from the system menu
71+
72+
73+
74+

build.bat

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
mkdir build
2+
cd build
3+
cmake ..
4+
cmake --build . --config Release

makever.c

-15.8 KB
Binary file not shown.

parsed104_tr_all.txt

-542 KB
Binary file not shown.

parsed104_with_addr.txt

-370 KB
Binary file not shown.

patchver.c

Lines changed: 245 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,245 @@
1+
#define _CRT_SECURE_NO_WARNINGS
2+
3+
#include <stdio.h>
4+
#include <stdlib.h>
5+
#include <string.h>
6+
7+
#pragma pack(1)
8+
typedef struct header_prg {
9+
int magic; // 0xa55a5aa5
10+
int file_length; //payload file lehght
11+
int file_crc; //payload file CRC32?
12+
int version;
13+
int volume; //1
14+
int zero1;
15+
char filename[16];
16+
char filedate[24];
17+
int zeros1[2];
18+
int ffs0[14]; //0xFF
19+
int magic1; // 0xa55a5aa5
20+
int zero2;
21+
int file_length_prg; //one more time - payload file lehght
22+
int file_crc1; //one more time - payload file CRC32?
23+
int magic2[3]; // const: 0x00104788, 0x04104788, 0x06000010
24+
int ffs1[16]; //0xFF
25+
int ffs2[16]; //0xFF
26+
int ffs3[16]; //0xFF
27+
int ffs4[16]; //0xFF
28+
int ffs5[16]; //0xFF
29+
int ffs6[8]; //0xFF
30+
int ver_crc; // up to
31+
} header_typeprg;
32+
33+
#pragma pack(1)
34+
typedef struct header_st {
35+
int magic; // 0xa55a5aa5 // 00
36+
int len; // len of ver file // 04
37+
int version; //version // 08
38+
int volume; //1 // 0C
39+
int zero1; // 10
40+
int a2c; //2c // 14
41+
int nb0_length; //payload file lehght //18
42+
int nb0_crc; //payload file CRC32? //1C
43+
int version1; // same version // 20
44+
int volume1; //1 // 24
45+
int zero2; // 28
46+
int nfiles; //1 // 2C
47+
int dirdepth; //1 // 30
48+
char dirname[64]; // 34
49+
int filestoprocess; //1 // 74
50+
char filename[56]; // 78
51+
int file_length; // B0
52+
int file_crc; // B4
53+
//----
54+
//int magic1; // 0xa55a5aa5 // B8
55+
//int ver_crc; // up to and including magic1 //BC
56+
} header_type;
57+
58+
59+
static const unsigned int crc32_table[] =
60+
{
61+
0x00000000, 0x77073096, 0xEE0E612C, 0x990951BA, 0x076DC419, 0x706AF48F, 0xE963A535, 0x9E6495A3,
62+
0x0EDB8832, 0x79DCB8A4, 0xE0D5E91E, 0x97D2D988, 0x09B64C2B, 0x7EB17CBD, 0xE7B82D07, 0x90BF1D91,
63+
0x1DB71064, 0x6AB020F2, 0xF3B97148, 0x84BE41DE, 0x1ADAD47D, 0x6DDDE4EB, 0xF4D4B551, 0x83D385C7,
64+
0x136C9856, 0x646BA8C0, 0xFD62F97A, 0x8A65C9EC, 0x14015C4F, 0x63066CD9, 0xFA0F3D63, 0x8D080DF5,
65+
0x3B6E20C8, 0x4C69105E, 0xD56041E4, 0xA2677172, 0x3C03E4D1, 0x4B04D447, 0xD20D85FD, 0xA50AB56B,
66+
0x35B5A8FA, 0x42B2986C, 0xDBBBC9D6, 0xACBCF940, 0x32D86CE3, 0x45DF5C75, 0xDCD60DCF, 0xABD13D59,
67+
0x26D930AC, 0x51DE003A, 0xC8D75180, 0xBFD06116, 0x21B4F4B5, 0x56B3C423, 0xCFBA9599, 0xB8BDA50F,
68+
0x2802B89E, 0x5F058808, 0xC60CD9B2, 0xB10BE924, 0x2F6F7C87, 0x58684C11, 0xC1611DAB, 0xB6662D3D,
69+
0x76DC4190, 0x01DB7106, 0x98D220BC, 0xEFD5102A, 0x71B18589, 0x06B6B51F, 0x9FBFE4A5, 0xE8B8D433,
70+
0x7807C9A2, 0x0F00F934, 0x9609A88E, 0xE10E9818, 0x7F6A0DBB, 0x086D3D2D, 0x91646C97, 0xE6635C01,
71+
0x6B6B51F4, 0x1C6C6162, 0x856530D8, 0xF262004E, 0x6C0695ED, 0x1B01A57B, 0x8208F4C1, 0xF50FC457,
72+
0x65B0D9C6, 0x12B7E950, 0x8BBEB8EA, 0xFCB9887C, 0x62DD1DDF, 0x15DA2D49, 0x8CD37CF3, 0xFBD44C65,
73+
0x4DB26158, 0x3AB551CE, 0xA3BC0074, 0xD4BB30E2, 0x4ADFA541, 0x3DD895D7, 0xA4D1C46D, 0xD3D6F4FB,
74+
0x4369E96A, 0x346ED9FC, 0xAD678846, 0xDA60B8D0, 0x44042D73, 0x33031DE5, 0xAA0A4C5F, 0xDD0D7CC9,
75+
0x5005713C, 0x270241AA, 0xBE0B1010, 0xC90C2086, 0x5768B525, 0x206F85B3, 0xB966D409, 0xCE61E49F,
76+
0x5EDEF90E, 0x29D9C998, 0xB0D09822, 0xC7D7A8B4, 0x59B33D17, 0x2EB40D81, 0xB7BD5C3B, 0xC0BA6CAD,
77+
0xEDB88320, 0x9ABFB3B6, 0x03B6E20C, 0x74B1D29A, 0xEAD54739, 0x9DD277AF, 0x04DB2615, 0x73DC1683,
78+
0xE3630B12, 0x94643B84, 0x0D6D6A3E, 0x7A6A5AA8, 0xE40ECF0B, 0x9309FF9D, 0x0A00AE27, 0x7D079EB1,
79+
0xF00F9344, 0x8708A3D2, 0x1E01F268, 0x6906C2FE, 0xF762575D, 0x806567CB, 0x196C3671, 0x6E6B06E7,
80+
0xFED41B76, 0x89D32BE0, 0x10DA7A5A, 0x67DD4ACC, 0xF9B9DF6F, 0x8EBEEFF9, 0x17B7BE43, 0x60B08ED5,
81+
0xD6D6A3E8, 0xA1D1937E, 0x38D8C2C4, 0x4FDFF252, 0xD1BB67F1, 0xA6BC5767, 0x3FB506DD, 0x48B2364B,
82+
0xD80D2BDA, 0xAF0A1B4C, 0x36034AF6, 0x41047A60, 0xDF60EFC3, 0xA867DF55, 0x316E8EEF, 0x4669BE79,
83+
0xCB61B38C, 0xBC66831A, 0x256FD2A0, 0x5268E236, 0xCC0C7795, 0xBB0B4703, 0x220216B9, 0x5505262F,
84+
0xC5BA3BBE, 0xB2BD0B28, 0x2BB45A92, 0x5CB36A04, 0xC2D7FFA7, 0xB5D0CF31, 0x2CD99E8B, 0x5BDEAE1D,
85+
0x9B64C2B0, 0xEC63F226, 0x756AA39C, 0x026D930A, 0x9C0906A9, 0xEB0E363F, 0x72076785, 0x05005713,
86+
0x95BF4A82, 0xE2B87A14, 0x7BB12BAE, 0x0CB61B38, 0x92D28E9B, 0xE5D5BE0D, 0x7CDCEFB7, 0x0BDBDF21,
87+
0x86D3D2D4, 0xF1D4E242, 0x68DDB3F8, 0x1FDA836E, 0x81BE16CD, 0xF6B9265B, 0x6FB077E1, 0x18B74777,
88+
0x88085AE6, 0xFF0F6A70, 0x66063BCA, 0x11010B5C, 0x8F659EFF, 0xF862AE69, 0x616BFFD3, 0x166CCF45,
89+
0xA00AE278, 0xD70DD2EE, 0x4E048354, 0x3903B3C2, 0xA7672661, 0xD06016F7, 0x4969474D, 0x3E6E77DB,
90+
0xAED16A4A, 0xD9D65ADC, 0x40DF0B66, 0x37D83BF0, 0xA9BCAE53, 0xDEBB9EC5, 0x47B2CF7F, 0x30B5FFE9,
91+
0xBDBDF21C, 0xCABAC28A, 0x53B39330, 0x24B4A3A6, 0xBAD03605, 0xCDD70693, 0x54DE5729, 0x23D967BF,
92+
0xB3667A2E, 0xC4614AB8, 0x5D681B02, 0x2A6F2B94, 0xB40BBE37, 0xC30C8EA1, 0x5A05DF1B, 0x2D02EF8D
93+
};
94+
95+
unsigned int crc32b(const unsigned char* data, int len) {
96+
97+
unsigned int crc;
98+
crc = 0xFFFFFFFF;
99+
100+
if (len) do {
101+
crc = (crc >> 8) ^ crc32_table[(crc ^ *data) & 255];
102+
data++;
103+
} while (--len);
104+
105+
return(~crc);
106+
}
107+
108+
unsigned int checksum32(const unsigned char* data, int len) {
109+
int i;
110+
unsigned int crc, tmp, tmp1;
111+
crc = 0x00000000;
112+
tmp = 0;
113+
tmp1 = 0;
114+
len = len / 4;
115+
116+
if (len > 0) do {
117+
118+
for (i = 0; i < 4; i++) {
119+
tmp1 = *data;
120+
tmp = tmp + (tmp1 << 8 * i);
121+
data++;
122+
}
123+
crc = crc + tmp;
124+
tmp = 0;
125+
126+
} while (--len);
127+
128+
return(crc);
129+
}
130+
131+
132+
133+
int main(int argc, char* argv[])
134+
{
135+
printf("Usage: patchver [PS140PLT.PRG] [PS140PLT.VER] [output.nb0]\n");
136+
137+
char* prg_filename = "PS140PLT.PRG";
138+
char* ver_filename = "PS140PLT.VER";
139+
char* nb0_filename = "output.nb0";
140+
141+
if (argc == 4)
142+
{
143+
prg_filename = argv[1];
144+
ver_filename = argv[2];
145+
nb0_filename = argv[3];
146+
}
147+
148+
printf("Patching: PRG='%s', VER='%s', NB0='%s' ...\n", prg_filename, ver_filename, nb0_filename);
149+
150+
// read content of nb0 file into memory
151+
FILE* nb0_file = fopen(nb0_filename, "rb");
152+
if (nb0_file == NULL)
153+
{
154+
printf("Can't read nb0 file with name '%s'\n", nb0_filename);
155+
exit(2);
156+
}
157+
fseek(nb0_file, 0L, SEEK_END);
158+
long nb0_file_size = ftell(nb0_file);
159+
fseek(nb0_file, 0L, SEEK_SET);
160+
void* nb0_buffer = malloc(nb0_file_size);
161+
if (nb0_buffer == NULL)
162+
{
163+
printf("Can't allocate memory for nb0!\n");
164+
exit(2);
165+
}
166+
fread(nb0_buffer, 1, nb0_file_size, nb0_file);
167+
fclose(nb0_file);
168+
printf("Read %d bytes from nb0 file with name '%s'\n", nb0_file_size, nb0_filename);
169+
170+
// read existing header of PRG file
171+
FILE* prg_file = fopen(prg_filename, "rb");
172+
if (prg_file == NULL)
173+
{
174+
printf("Can't open PRG file with name '%s'\n", prg_filename);
175+
exit(2);
176+
}
177+
header_typeprg prg_header;
178+
fread(&prg_header, sizeof(header_typeprg), 1, prg_file);
179+
fclose(prg_file);
180+
181+
printf("Read original PRG header version=%x , date='%s'\n", prg_header.version, prg_header.filedate);
182+
183+
// patching PRG header
184+
prg_header.file_length_prg = prg_header.file_length = nb0_file_size;
185+
int old_prg_version = prg_header.version;
186+
prg_header.version = prg_header.version + 1;
187+
prg_header.file_crc = prg_header.file_crc1 = checksum32(nb0_buffer, nb0_file_size);
188+
prg_header.ver_crc = checksum32(&prg_header, sizeof(prg_header) - 4);
189+
190+
long prg_file_new_size = nb0_file_size + sizeof(prg_header);
191+
unsigned char* prg_buffer = malloc(prg_file_new_size);
192+
memcpy(prg_buffer, &prg_header, sizeof(prg_header));
193+
memcpy(prg_buffer + sizeof(prg_header), nb0_buffer, nb0_file_size);
194+
195+
FILE* prg_file_new = fopen(prg_filename, "wb");
196+
fwrite(prg_buffer, 1, prg_file_new_size, prg_file_new);
197+
fclose(prg_file_new);
198+
199+
printf("PRG file '%s' successfully patched version %x -> %x .\n", prg_filename, old_prg_version, prg_header.version);
200+
201+
//reading existing header from VER file
202+
FILE* ver_file = fopen(ver_filename, "rb");
203+
if (ver_file == NULL)
204+
{
205+
printf("Can't open VER file with name '%s'\n", ver_filename);
206+
exit(2);
207+
}
208+
fseek(ver_file, 0L, SEEK_END);
209+
long ver_file_size = ftell(ver_file);
210+
fseek(ver_file, 0L, SEEK_SET);
211+
212+
unsigned char* ver_buffer = malloc(ver_file_size);
213+
fread(ver_buffer, 1, ver_file_size, ver_file);
214+
fclose(ver_file);
215+
216+
217+
//patching VER header
218+
header_type* ver_header = (header_type*)ver_buffer;
219+
char filename_ansi[1024];
220+
wcstombs(filename_ansi, ver_header->filename, 1024);
221+
if (strcmp(filename_ansi, prg_filename) != 0)
222+
{
223+
printf("Can't replace file with name '%s' to '%s' in VER file\n", filename_ansi, prg_filename);
224+
exit(2);
225+
}
226+
227+
int old_ver_version = ver_header->version;
228+
ver_header->version = ver_header->version1 = ver_header->version + 1;
229+
ver_header->nb0_length = prg_header.file_length;
230+
ver_header->nb0_crc = prg_header.file_crc;
231+
ver_header->file_length = prg_file_new_size;
232+
ver_header->file_crc = crc32b(prg_buffer, prg_file_new_size);
233+
int* ver_crc_ptr = (int*)(ver_buffer + ver_file_size - 4);
234+
*ver_crc_ptr = crc32b(ver_buffer, ver_file_size - 4);
235+
236+
//reading existing header from VER file
237+
FILE* ver_file_new = fopen(ver_filename, "wb");
238+
fwrite(ver_buffer, 1, ver_file_size, ver_file_new);
239+
fclose(ver_file_new);
240+
241+
printf("VER file '%s' successfully patched. version %x -> %x .\n", ver_filename, old_ver_version, ver_header->version);
242+
243+
printf("OK\n");
244+
245+
}

translate.c

1.6 KB
Binary file not shown.

0 commit comments

Comments
 (0)