Skip to content

aarch64-switch-rs/cargo-nx

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

36 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

cargo-nx

Introduction

cargo-nx is a simple build command for projects based on this organization's libraries and tools, to avoid having to mess with makefiles, scripts or having several copies of the same linker/target files for every single project, while also including support for generating various formats after projects are compiled.

Installation

Assuming you have Rust and cargo installed, it's just a matter of two steps:

  1. If not already installed, install rust-src:

    rustup component add rust-src
  2. Install cargo-nx:

    cargo install cargo-nx --git https://github.com/aarch64-switch-rs/cargo-nx

Usage

The program can be executed as cargo-nx or simply as a cargo subcommand, cargo nx, and it provides the following main subcommands:

new subcommand

This subcommand is quite similar to the usual cargo new subcommand.

Base format: cargo nx new <path> [<params/flags>]

Available parameters/flags

  • --name: Specify the package name (default is the input path's directory name)

  • --edition: Specify the package edition (available editions: [2015, 2018, 2021], default is 2021)

  • --type <package type>: Specify the package type to create. lib, nro, and nsp are available, with nro being the default.

build subcommand

This subcommand is quite similar to the normal cargo build subcommand.

Base format: cargo nx build [<params/flags>]

Available parameters/flags:

  • -r, --release: Builds on release profile, same as the normal cargo build --release option.

  • -p <path>, --path=<path>: Specifies a path with a crate to build (containing Cargo.toml, etc.), since the current directory is used by default otherwise.

  • -t <triple>, --target=<triple>: Specifies the target triple (which can be a target JSON like with regular cargo build); "aarch64-nintendo-switch-freestanding" (official tier 3 target) is used by default.

  • -v, --verbose: Displays extra information during the build process.

Package formats

Build format fields used for building must be placed placed inside [package.metadata.nx.<format>] in Cargo.toml. These fields vary depending on the project's format.

The program itself detects the target format when parsing Cargo.toml. Note that multiple formats at the same time are not currently supported.

Projects without specific build format fields, like libraries, can also be compiled. This can be useful to later generate custom executables instead of being generated by this subcommand.

NRO

Projects which generate homebrew NRO binaries don't have any mandatory fields, but only optional ones.

  • Example:
[package]
name = "Project"
version = "0.1.0"
authors = ["XorTroll"]
edition = "2021"

[package.metadata.nx.nro]
romfs = "romfs_dir"
icon = "icon.jpg"
nacp = { default_name = "Sample project", default_author = "XorTroll", version = "0.1 beta" }

Note: the romfs and icon fields must point to items located relative to the project's directory

The fields present on the nacp object, all of them optional, are the following:

Field Value Description Default value
default_name String (max size 0x200) Default title name Unknown application
default_author String (max size 0x100) Default application author Unknown author
version String (max size 0x10) Application version
application_id Hex-String u64 Application ID 0000000000000000
add_on_content_base_id Hex-String u64 Base ID for add-on content (DLC) application_id + 0x1000
titles Object of language titles Language-specific application name/author values Default values above
presence_group_id Hex-String u64 Presence group ID application_id
save_data_owner_id Hex-String u64 Save-data owner ID application_id
isbn String (max size 0x25) ISBN Empty string
startup_user_account "None", "Required", "RequiredWithNetworkServiceAccountAvailable" Whether the application requires a user account on launch "None"
attribute "None", "Demo", "RetailInteractiveDisplay" Application attribute "None"
screenshot "Allow", "Deny" Screenshot control "Allow"
video_capture "Disabled", "Enabled", "Automatic" Video capture control "Disabled"
logo_type "LicensedByNintendo", "Nintendo" Logo type "LicensedByNintendo"
logo_handling "Auto", "Manual" Logo handling "Auto"
crash_report "Deny", "Allow" Crash report control "Allow"
bcat_passphrase String (max size 0x41) BCAT passphrase Empty string
program_index u8 Program index 0

Note: default name/author and application ID are not actual NACP fields, but they are used as the default value for various fields, as the table shows.

Available languages

Language names Language codes
AmericanEnglish en-US
BritishEnglish en-UK
Japanese ja
French fr
German de
LatinAmericanSpanish es-419
Spanish es
Italian it
Dutch nl
CanadianFrench fr-CA
Portuguese pt
Russian ru
Korean ko
TraditionalChinese zh-TW
SimplifiedChinese zh-CN
BrazilianPortuguese pt-BR

Note: languages in the titles object can be specified by their names or their codes, as the JSON example above shows.

  • Example with specific languages:
[package]
name = "Multi-language"
version = "0.2.0"
authors = ["XorTroll"]
edition = "2021"

[package.metadata.nx.nro.nacp]
default_name = "A"
default_author = "B"
version = "0.2 beta"
titles = { ja = { name = "J" }, LatinAmericanSpanish = { author = "X" }, it = { name = "I", author = "T" } }
Names/authors produced above:

- Japanese: "J", "B"
- LatinAmericanSpanish: "A", "X"
- Italian: "I", "T"
- Other languages: "A", "B"

Note: only name and author fields can be language-specific

NSP

Projects which generate sysmodule NSP exefs packages need a single, mandatory field for the NPDM data, which would be npdm for specifying it on the TOML itself or npdm_json for using an external JSON file:

  • Example:
[package]
name = "Project"
version = "0.2.10"
authors = ["XorTroll"]
edition = "2021"

[package.metadata.nx.nsp.npdm]
name = "ProjectNpdm"
signature_key_generation = 0
main_thread_stack_size = "0x20000"
main_thread_priority = 49
main_thread_core_number = 3
system_resource_size = 0
version = 0
address_space_type = 1
is_64_bit = true
optimize_memory_allocation = false
disable_device_address_space_merge = false
is_production = true
unqualified_approval = false
memory_region = 2
program_id = "0x0100AAAABBBBCCCC"

[package.metadata.nx.nsp.npdm.fs_access_control]
flags = "0xFFFFFFFFFFFFFFFF"

[package.metadata.nx.nsp.npdm.service_access_control]
accessed_services = [ "fsp-srv", "ncm" ]
hosted_services = [ "demo:srv" ]

[package.metadata.nx.nsp.npdm.kernel_capabilities]
highest_priority = 63
lowest_priority = 16
max_core_number = 3
min_core_number = 3
enable_system_calls = [
    "SetHeapSize"
]
kernel_version = "3.0"
  • Example using an external NPDM JSON:
[package]
name = "Project"
version = "0.2.10"
authors = ["XorTroll"]
edition = "2021"

[package.metadata.nx.nsp]
npdm_json = "npdm.json"

Note: the NPDM JSON file follows the same format used in most other homebrews (check projects like Atmosphere, emuiibo, ldn_mitm...) and, like with the paths in the NRO format, it must be relative to the project's directory

Libraries

Library projects have nothing special in their Cargo.toml

TODO

  • Implement more useful commands from regular cargo build/new, etc.

  • Maybe bundle some basic target JSON+LDs different from the official tier 3 one? (32-bit or w/ crypto support, for instance)

Credits

  • linkle libraries as the core element of this project
  • cargo-count as the example followed to make a cargo subcommand project
  • Icons8 for using one of their Nintendo Switch icons as the base for the default NRO icon

About

Cargo subcommand to simplify building Nintendo Switch projects

Topics

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Sponsor this project

Packages

No packages published

Languages