dropped aas, moved to maxmod
[gbajam21] / tools / mmutil / nds.c
1 /****************************************************************************
2  *                                                          __              *
3  *                ____ ___  ____ __  ______ ___  ____  ____/ /              *
4  *               / __ `__ \/ __ `/ |/ / __ `__ \/ __ \/ __  /               *
5  *              / / / / / / /_/ />  </ / / / / / /_/ / /_/ /                *
6  *             /_/ /_/ /_/\__,_/_/|_/_/ /_/ /_/\____/\__,_/                 *
7  *                                                                          *
8  *         Copyright (c) 2008, Mukunda Johnson (mukunda@maxmod.org)         *
9  *                                                                          *
10  * Permission to use, copy, modify, and/or distribute this software for any *
11  * purpose with or without fee is hereby granted, provided that the above   *
12  * copyright notice and this permission notice appear in all copies.        *
13  *                                                                          *
14  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES *
15  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF         *
16  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR  *
17  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES   *
18  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN    *
19  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF  *
20  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.           *
21  ****************************************************************************/
22
23 /* NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE 
24   SOME CODE WAS STOLEN FROM NDSTOOL.CPP
25 NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE  */
26
27 #include <stdlib.h>
28 #include "defs.h"
29 #include "files.h"
30 #include "mas.h"
31
32 #include "arm7_st.inc"
33 #include "arm9_st.inc"
34
35 const u8 nds_logo[];
36
37 #define ARM7_SIZE sizeof(arm7_bin)
38 #define ARM9_SIZE sizeof(arm9_bin)
39
40 const unsigned short crc16tab[] =
41 {
42         0x0000, 0xC0C1, 0xC181, 0x0140, 0xC301, 0x03C0, 0x0280, 0xC241,
43         0xC601, 0x06C0, 0x0780, 0xC741, 0x0500, 0xC5C1, 0xC481, 0x0440,
44         0xCC01, 0x0CC0, 0x0D80, 0xCD41, 0x0F00, 0xCFC1, 0xCE81, 0x0E40,
45         0x0A00, 0xCAC1, 0xCB81, 0x0B40, 0xC901, 0x09C0, 0x0880, 0xC841,
46         0xD801, 0x18C0, 0x1980, 0xD941, 0x1B00, 0xDBC1, 0xDA81, 0x1A40,
47         0x1E00, 0xDEC1, 0xDF81, 0x1F40, 0xDD01, 0x1DC0, 0x1C80, 0xDC41,
48         0x1400, 0xD4C1, 0xD581, 0x1540, 0xD701, 0x17C0, 0x1680, 0xD641,
49         0xD201, 0x12C0, 0x1380, 0xD341, 0x1100, 0xD1C1, 0xD081, 0x1040,
50         0xF001, 0x30C0, 0x3180, 0xF141, 0x3300, 0xF3C1, 0xF281, 0x3240,
51         0x3600, 0xF6C1, 0xF781, 0x3740, 0xF501, 0x35C0, 0x3480, 0xF441,
52         0x3C00, 0xFCC1, 0xFD81, 0x3D40, 0xFF01, 0x3FC0, 0x3E80, 0xFE41,
53         0xFA01, 0x3AC0, 0x3B80, 0xFB41, 0x3900, 0xF9C1, 0xF881, 0x3840,
54         0x2800, 0xE8C1, 0xE981, 0x2940, 0xEB01, 0x2BC0, 0x2A80, 0xEA41,
55         0xEE01, 0x2EC0, 0x2F80, 0xEF41, 0x2D00, 0xEDC1, 0xEC81, 0x2C40,
56         0xE401, 0x24C0, 0x2580, 0xE541, 0x2700, 0xE7C1, 0xE681, 0x2640,
57         0x2200, 0xE2C1, 0xE381, 0x2340, 0xE101, 0x21C0, 0x2080, 0xE041,
58         0xA001, 0x60C0, 0x6180, 0xA141, 0x6300, 0xA3C1, 0xA281, 0x6240,
59         0x6600, 0xA6C1, 0xA781, 0x6740, 0xA501, 0x65C0, 0x6480, 0xA441,
60         0x6C00, 0xACC1, 0xAD81, 0x6D40, 0xAF01, 0x6FC0, 0x6E80, 0xAE41,
61         0xAA01, 0x6AC0, 0x6B80, 0xAB41, 0x6900, 0xA9C1, 0xA881, 0x6840,
62         0x7800, 0xB8C1, 0xB981, 0x7940, 0xBB01, 0x7BC0, 0x7A80, 0xBA41,
63         0xBE01, 0x7EC0, 0x7F80, 0xBF41, 0x7D00, 0xBDC1, 0xBC81, 0x7C40,
64         0xB401, 0x74C0, 0x7580, 0xB541, 0x7700, 0xB7C1, 0xB681, 0x7640,
65         0x7200, 0xB2C1, 0xB381, 0x7340, 0xB101, 0x71C0, 0x7080, 0xB041,
66         0x5000, 0x90C1, 0x9181, 0x5140, 0x9301, 0x53C0, 0x5280, 0x9241,
67         0x9601, 0x56C0, 0x5780, 0x9741, 0x5500, 0x95C1, 0x9481, 0x5440,
68         0x9C01, 0x5CC0, 0x5D80, 0x9D41, 0x5F00, 0x9FC1, 0x9E81, 0x5E40,
69         0x5A00, 0x9AC1, 0x9B81, 0x5B40, 0x9901, 0x59C0, 0x5880, 0x9841,
70         0x8801, 0x48C0, 0x4980, 0x8941, 0x4B00, 0x8BC1, 0x8A81, 0x4A40,
71         0x4E00, 0x8EC1, 0x8F81, 0x4F40, 0x8D01, 0x4DC0, 0x4C80, 0x8C41,
72         0x4400, 0x84C1, 0x8581, 0x4540, 0x8701, 0x47C0, 0x4680, 0x8641,
73         0x8201, 0x42C0, 0x4380, 0x8341, 0x4100, 0x81C1, 0x8081, 0x4040
74 };
75
76 void Write_NDS( void )
77 {
78         int x;
79         const char game_title[] = "SOUND TEST ";
80
81         for( x = 0; x < 12; x++ )
82                 write8( game_title[x] );
83
84         write32( '####' );      // gamecode
85         write16( 0 );   // makercode
86         write8( 0 );    // unit code (Nintendo DS)
87         write8( 0 );    // encryption seed
88         write8( 0 );    // device capability
89         for( x=  0; x < 9; x++ )
90                 write8( 0 );    // reserved
91         write8( 0 );    // rom version
92         write8( 4 );    // autostart
93
94 //-----------------------------------------------------------
95         write32( 512+32768 ); // arm9 ROM offset
96         write32( 0x2000000 ); // arm9 entry point
97         write32( 0x2000000 ); // arm9 ram address
98         write32( 65536 ); // arm9 binary size (modify later)
99 //-----------------------------------------------------------
100         write32( 512 );                 // arm7 ROM offset
101         write32( 0x37f8000 );   // arm7 entry point
102         write32( 0x37f8000 );   // arm7 ram address
103         write32( 32768 );       // arm7 binary size
104 //-----------------------------------------------------------
105         
106         write32( 0 );                   // fnt address
107         write32( 0 );                   // fnt size
108         write32( 0 );                   // fat address
109         write32( 0 );                   // fat size
110
111         write32( 0 );                   // file arm9 overlay address
112         write32( 0 );                   // file arm9 overlay size
113         write32( 0 );                   // file arm7 overlay address
114         write32( 0 );                   // file arm7 overlay size
115         
116         write32( 0x7f7fff );    // port 40001a4 setting for normal commands
117         write32( 0x203f1fff );  // port 40001a4 setting for KEY1 commands
118         
119         write32( 0 );                   // icon (no icon)
120         
121         write16( 0 );                   // secure area checksum
122         write16( 0x51e );               // secure area loading timeout
123         write32( 0 );                   // arm9 auto load list RAM address (?)
124         write32( 0 );                   // arm7 auto load list RAM address (?)
125         write32( 0 );                   // secure area disable
126         write32( 0 );                   // secure area disable
127         
128         write32( 0x14400 );             // total used ROM size
129         write32( 0x200 );               // rom header size
130         
131         write32( 0 );
132         write32( 0 );
133         write32( 0 );
134         write32( 0 );
135         write32( 0 );
136         write32( 0 );
137         write32( 'MARS' );
138         write32( '11V_' );
139         write8( '0' );
140         write8( 0 );write8( 0 );write8( 0 );
141         write32( 'SSAP' );
142         write8( '0' );write8( '1' );write8( 0x96 );write8( 0 );
143
144         write32( 0 );
145         write32( 0 );
146         write32( 0 );
147
148         for( x = 0; x < 0x9c; x++ )
149                 write8( nds_logo[x] );          // NINTENDO LOGO
150
151         write16( 0x9e1a );              // nintendo logo checksum
152         write16( 0 );                   // header checksum (modify later)
153         write32( 0 );                   // debug rom offset
154         write32( 0 );                   // debug rom size
155         write32( 0 );                   // debug ram address
156
157         write32( 0 );                   // reserved
158
159         for( x = 0; x < 0x90; x++ )
160                 write8( 0 );
161
162         // write binaries
163         for( x = 0; x < ARM7_SIZE; x++ )
164                 write8( arm7_bin[x] );
165         for( x = 0; x < 32768-ARM7_SIZE; x++ )  // pad to 32k
166                 write8( (u8)x );
167         for( x = 0; x < ARM9_SIZE; x++ )
168                 write8( arm9_bin[x] );
169         for( x = 0; x < 65536-ARM9_SIZE; x++ )  // pad to 64k
170                 write8( (u8)x );
171 }
172
173 unsigned short calculate_crc( void )
174 {
175         int i;
176         unsigned short crc = 0xFFFF;
177         for ( i=0; i<0x15E; i++)
178         {
179                 unsigned char data = read8();
180                 crc = (crc >> 8) ^ crc16tab[(crc ^ data) & 0xFF];
181         }
182         return crc;
183 }
184
185 void Validate_NDS( char* filename, int output_size )
186 {
187         int arm9_size;
188         int header_crc;
189         arm9_size = 65536 + output_size;
190         file_open_write_end( filename );
191         file_seek_write( 0x2c, SEEK_SET );
192         write32( arm9_size );
193         file_seek_write( 0x80, SEEK_SET );
194         write32( arm9_size+32768 );             // total used rom size
195         file_close_write();
196
197         file_open_read( filename );
198         header_crc=calculate_crc();
199         file_close_read();
200         header_crc &= 0xFFFF;
201
202         file_open_write_end( filename );
203         file_seek_write( 0x15e, SEEK_SET );
204         write16( (u16)header_crc );
205         file_close_write();
206         /*
207         // write arm7 rom_offset
208         file_seek_write( 0x30, SEEK_SET );
209         write32( 512 );
210
211         // write arm9 rom_offset
212         file_seek_write( 0x20, SEEK_SET );
213         write32( 512 + 0x4000 );
214
215         // write arm9 size
216         file_seek_write( 0x2C, SEEK_SET );
217         write32( 0x10000 + output_size );
218         */
219 }
220
221 const u8 nds_logo[] = {
222         0xC8, 0x60, 0x4F, 0xE2, 0x1, 0x70, 0x8F, 0xE2, 0x17, 0xFF, 0x2F, 0xE1, 0x12, 0x4F, 0x11, 0x48, 0x12, 0x4C, 0x20, 0x60, 0x64, 0x60, 0x7C, 0x62, 0x30, 0x1C, 0x39, 0x1C, 0x10, 0x4A, 0x0, 0xF0, 0x14, 0xF8, 
223 0x30, 0x6A, 0x80, 0x19, 0xB1, 0x6A, 0xF2, 0x6A, 0x0, 0xF0, 0xB, 0xF8, 0x30, 0x6B, 0x80, 0x19, 0xB1, 0x6B, 0xF2, 0x6B, 0x0, 0xF0, 0x8, 0xF8, 0x70, 0x6A, 0x77, 0x6B, 0x7, 0x4C, 0x60, 0x60, 0x38, 0x47, 0x7, 
224 0x4B, 0xD2, 0x18, 0x9A, 0x43, 0x7, 0x4B, 0x92, 0x8, 0xD2, 0x18, 0xC, 0xDF, 0xF7, 0x46, 0x4, 0xF0, 0x1F, 0xE5, 0x0, 0xFE, 0x7F, 0x2, 0xF0, 0xFF, 0x7F, 0x2, 0xF0, 0x1, 0x0, 0x0, 0xFF, 0x1, 0x0, 0x0, 0x0, 
225 0x0, 0x0, 0x4, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 
226 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, };