| 155 | } |
| 156 | |
| 157 | bool patchApplyUPS(MFILE * f, u8 **rom, int *size) { |
| 158 | |
| 159 | s64 srcCRC, dstCRC, patchCRC; |
| 160 | |
| 161 | memfseek(f, 0, MSEEK_END); |
| 162 | long int patchSize = memftell(f); |
| 163 | if (patchSize < 20) { |
| 164 | return false; |
| 165 | } |
| 166 | |
| 167 | memfseek(f, 0, MSEEK_SET); |
| 168 | |
| 169 | if (memfgetc(f) != 'U' || memfgetc(f) != 'P' || memfgetc(f) != 'S' |
| 170 | || memfgetc(f) != '1') { |
| 171 | return false; |
| 172 | } |
| 173 | |
| 174 | memfseek(f, -12, MSEEK_END); |
| 175 | srcCRC = readInt4(f); |
| 176 | dstCRC = readInt4(f); |
| 177 | patchCRC = readInt4(f); |
| 178 | if (srcCRC == -1 || dstCRC == -1 || patchCRC == -1) { |
| 179 | return false; |
| 180 | } |
| 181 | |
| 182 | memfseek(f, 0, MSEEK_SET); |
| 183 | u32 crc = computePatchCRC(f, patchSize - 4); |
| 184 | |
| 185 | if (crc != patchCRC) { |
| 186 | return false; |
| 187 | } |
| 188 | |
| 189 | crc = crc32(0L, Z_NULL, 0); |
| 190 | crc = crc32(crc, *rom, *size); |
| 191 | |
| 192 | memfseek(f, 4, MSEEK_SET); |
| 193 | s64 dataSize; |
| 194 | s64 srcSize = readVarPtr(f); |
| 195 | s64 dstSize = readVarPtr(f); |
| 196 | |
| 197 | if (crc == srcCRC) { |
| 198 | dataSize = srcSize; |
| 199 | } else if (crc == dstCRC) { |
| 200 | dataSize = dstSize; |
| 201 | } else { |
| 202 | return false; |
| 203 | } |
| 204 | if (dataSize != *size) { |
| 205 | return false; |
| 206 | } |
| 207 | |
| 208 | s64 relative = 0; |
| 209 | u8 *mem; |
| 210 | while (memftell(f) < patchSize - 12) { |
| 211 | relative += readVarPtr(f); |
| 212 | if (relative > dataSize) |
| 213 | continue; |
| 214 | mem = *rom + relative; |
no test coverage detected