Skip to content

Commit

Permalink
CICKind.get_entrypoint
Browse files Browse the repository at this point in the history
  • Loading branch information
AngheloAlf committed Jan 11, 2024
1 parent 2f71eab commit c7ab4da
Show file tree
Hide file tree
Showing 5 changed files with 41 additions and 5 deletions.
5 changes: 5 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,11 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

## [Unreleased]

### Added

- `CICKind.get_entrypoint`: Returns the entrypoint address that would be used
on runtime.

### Changed

- Rewrite the checksum algorithm for readability and simplicity.
Expand Down
2 changes: 2 additions & 0 deletions bindings/c/include/ipl3checksum/cickinds.h
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,8 @@ uint32_t ipl3checksum_cickind_get_seed(Ipl3Checksum_CICKind self);

uint32_t ipl3checksum_cickind_get_magic(Ipl3Checksum_CICKind self);

uint32_t ipl3checksum_cickind_get_entrypoint(Ipl3Checksum_CICKind self, uint32_t header_entrypoint);

/**
* Returns the md5 hash for the specified CIC kind.
*
Expand Down
8 changes: 8 additions & 0 deletions src/ipl3checksum/cickinds.pyi
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ class CICKind():
def getSeed(self) -> int:
"""
Seed value set by the PIF ROM before the CPU (and the IPL3) is executed.
https://n64brew.dev/wiki/PIF-NUS#IPL3_checksum_algorithm
"""

Expand All @@ -28,6 +29,13 @@ class CICKind():
Magic value hardcoded inside the IPL3 itself
"""

def getEntrypoint(self, header_entrypoint: int) -> int:
"""
Calculates the actual entrypoint address based on the entrypoint specified on the header.
CIC 7102 is a notable case since its IPL3 hardcodes it, ignoring the entrypoint from the header.
"""

def getHashMd5(self) -> str:
"""
Expected md5 hash of the IPL3 blob
Expand Down
6 changes: 1 addition & 5 deletions src/rs/checksum.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,11 +7,7 @@ use crate::{detect, error::Ipl3ChecksumError, utils};
fn get_entrypoint_addr(rom_bytes: &[u8], kind: CICKind) -> Result<u32, Ipl3ChecksumError> {
let entrypoint_addr: u32 = utils::read_u32(rom_bytes, 8)?;

match kind {
CICKind::CIC_X103 | CICKind::CIC_5101 => Ok(entrypoint_addr.wrapping_sub(0x100000)),
CICKind::CIC_X106 => Ok(entrypoint_addr.wrapping_sub(0x200000)),
_ => Ok(entrypoint_addr),
}
Ok(kind.get_entrypoint(entrypoint_addr))
}

const HEADER_IPL3_SIZE: usize = 0x1000;
Expand Down
25 changes: 25 additions & 0 deletions src/rs/cickinds.rs
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,9 @@ pub enum CICKind {
}

impl CICKind {
/// Seed value set by the PIF ROM before the CPU (and the IPL3) is executed.
///
/// https://n64brew.dev/wiki/PIF-NUS#IPL3_checksum_algorithm
pub fn get_seed(&self) -> u32 {
match self {
Self::CIC_6101 | Self::CIC_6102_7101 | Self::CIC_7102 => 0x3F,
Expand All @@ -37,13 +40,26 @@ impl CICKind {
}
}

/// Magic value hardcoded inside the IPL3 itself
pub fn get_magic(&self) -> u32 {
match self {
Self::CIC_6101 | Self::CIC_6102_7101 | Self::CIC_7102 | Self::CIC_X105 => 0x5D588B65,
Self::CIC_X103 | Self::CIC_X106 | Self::CIC_5101 => 0x6C078965,
}
}

/// Calculates the actual entrypoint address based on the entrypoint specified on the header.
///
/// CIC 7102 is a notable case since its IPL3 hardcodes it, ignoring the entrypoint from the header.
pub fn get_entrypoint(&self, header_entrypoint: u32) -> u32 {
match self {
CICKind::CIC_7102 => 0x80000480,
CICKind::CIC_X103 | CICKind::CIC_5101 => header_entrypoint.wrapping_sub(0x100000),
CICKind::CIC_X106 => header_entrypoint.wrapping_sub(0x200000),
_ => header_entrypoint,
}
}

pub fn get_hash_md5(&self) -> &'static str {
match self {
Self::CIC_6101 => "900b4a5b68edb71f4c7ed52acd814fc5",
Expand Down Expand Up @@ -163,6 +179,10 @@ mod python_bindings {
self.get_magic()
}

pub fn getEntrypoint(&self, header_entrypoint: u32) -> u32 {
self.get_entrypoint(header_entrypoint)
}

pub fn getHashMd5(&self) -> &str {
self.get_hash_md5()
}
Expand Down Expand Up @@ -226,6 +246,11 @@ mod c_bindings {
kind.get_magic()
}

#[no_mangle]
pub extern "C" fn ipl3checksum_cickind_get_entrypoint(kind: CICKind, header_entrypoint: u32) -> u32 {
kind.get_entrypoint(header_entrypoint)
}

#[no_mangle]
pub extern "C" fn ipl3checksum_cickind_get_hash_md5(
kind: CICKind,
Expand Down

0 comments on commit c7ab4da

Please sign in to comment.