Difference between revisions of "NV services"
(minor stuff) |
|||
Line 494: | Line 494: | ||
=== NVGPU_IOCTL_CHANNEL_SUBMIT_GPFIFO === | === NVGPU_IOCTL_CHANNEL_SUBMIT_GPFIFO === | ||
− | Submits a gpfifo object. Modified to take inline | + | Submits a gpfifo object. Modified to take inline entry objects instead of a pointer. |
struct fence { | struct fence { | ||
Line 587: | Line 587: | ||
Submits a gpfifo object (async version). Exclusive to the Switch. | Submits a gpfifo object (async version). Exclusive to the Switch. | ||
− | |||
− | |||
− | |||
− | |||
− | |||
struct { | struct { | ||
− | u64 __gpfifo; | + | u64 __gpfifo; // in (pointer to gpfifo fence structs; ignored) |
− | u32 __num_entries; | + | u32 __num_entries; // in (number of fence objects being submitted) |
− | u32 __flags; | + | u32 __flags; // in |
− | struct fence __fence_out; // out (returned new fence object for others to wait on) | + | struct fence __fence_out; // out (returned new fence object for others to wait on) |
− | struct | + | struct gpfifo_entry __entries[]; // in (depends on __num_entries) |
− | |||
}; | }; | ||
=== NVGPU_IOCTL_CHANNEL_ALLOC_GPFIFO_EX2 === | === NVGPU_IOCTL_CHANNEL_ALLOC_GPFIFO_EX2 === | ||
Allocates gpfifo entries with additional parameters and returns a fence. Exclusive to the Switch. | Allocates gpfifo entries with additional parameters and returns a fence. Exclusive to the Switch. | ||
− | |||
− | |||
− | |||
− | |||
− | |||
struct { | struct { |
Revision as of 16:29, 3 June 2017
The Switch makes use of a customized NVIDIA driver.
nvdrv:a
Main NVIDIA driver service.
Cmd | Name |
---|---|
0 | #Open |
1 | #Ioctl |
2 | #Close |
3 | #Initialize |
4 | QueryEvent |
5 | MapSharedMem |
6 | ? |
7 | ? |
8 | BindDisplayService |
9 | ? |
Open
Word | Value |
---|---|
0 | 0x00100004 |
1 | 0x00000008 |
2-4 | Type 5 descriptor: Device path |
0-1 | "SFCI" |
2-3 | Cmd id (0) |
Ioctl
Word | Value |
---|---|
0 | 0x11100004 |
1 | 0x00000C0B |
? | Type 0x21 descriptor: Input buffer |
? | Type 0x22 descriptor: Output buffer |
0-1 | "SFCI" |
2-3 | Cmd id (1) |
4 | Device fd |
5 | Ioctl Cmd |
Close
Word | Value |
---|---|
0 | 0x00000004 |
1 | 0x00000009 |
0-1 | "SFCI" |
2-3 | Cmd id (2) |
4 | Device fd |
Initialize
Word | Value |
---|---|
0 | 0x00000004 |
1 | 0x80000009 |
? | Handle descriptor: Current process |
? | Handle descriptor: Shared memory mirror |
0-1 | "SFCI" |
2-3 | Cmd id (3) |
4 | Shared memory size |
Webkit applet creates the shared memory with perm = 0 and size 0x300000.
Ioctls
The ioctl number is generated with the following primitive (see Linux kernel):
#define _IOC(inout, group, num, len) \ (inout | ((len & IOCPARM_MASK) << 16) | ((group) << 8) | (num))
The following table contains known ioctls.
/dev/nvhost-ctrl
Value | Direction | Size | Description | Notes |
---|---|---|---|---|
0xC0080014 | Inout | 8 | NVHOST_IOCTL_CTRL_SYNCPT_READ | |
0x40040015 | In | 4 | NVHOST_IOCTL_CTRL_SYNCPT_INCR | |
0xC00C0016 | Inout | 12 | NVHOST_IOCTL_CTRL_SYNCPT_WAIT | |
0x40080017 | In | 8 | NVHOST_IOCTL_CTRL_MODULE_MUTEX | |
0xC0180018 | Inout | 24 | NVHOST32_IOCTL_CTRL_MODULE_REGRDWR | |
0xC0100019 | Inout | 16 | NVHOST_IOCTL_CTRL_SYNCPT_WAITEX | |
0xC008001A | Inout | 8 | NVHOST_IOCTL_CTRL_SYNCPT_READ_MAX | |
0xC004001C | Inout | 4 | ||
0xC010001D | Inout | 16 | NvRmSyncWaitEvent (wait on event?) | |
0xC010001E | Inout | 16 | NvRmSyncWaitEvent (wait on event?) | |
0xC004001F | Inout | 4 | NvRmSyncWaitEvent (signal event?) | |
0xC0040020 | Inout | 4 | NvRmSyncWaitEvent (signal event?) | |
0x40080021 | In | 8 | cancel_wait_event | Cancels all events |
/dev/nvhost-as-gpu
Each fd opened to this device creates an address space. An address space is then later bound with a channel.
Once a nvgpu channel has been bound to an address space it cannot be unbound. There is no support for allowing an nvgpu channel to change from one address space to another (or from one to none).
Device | Direction | Size | Value | Description | Notes |
---|---|---|---|---|---|
/dev/nvhost-as-gpu | In | 4 | 0x40044101 | #NVGPU_AS_IOCTL_BIND_CHANNEL | |
/dev/nvhost-as-gpu | Inout | 24 | 0xC0184102 | #NVGPU_AS_IOCTL_ALLOC_SPACE | |
/dev/nvhost-as-gpu | Inout | 16 | 0xC0104103 | #NVGPU_AS_IOCTL_FREE_SPACE | |
/dev/nvhost-as-gpu | Inout | 24 | 0xC0184104 | #NVGPU_AS_IOCTL_MAP_BUFFER | |
/dev/nvhost-as-gpu | Inout | 8 | 0xC0084105 | #NVGPU_AS_IOCTL_UNMAP_BUFFER | |
/dev/nvhost-as-gpu | Inout | 40 | 0xC0284106 | NVGPU_AS_IOCTL_MAP_BUFFER_EX | |
/dev/nvhost-as-gpu | In | 16 | 0x40104107 | #NVGPU_AS_IOCTL_INITIALIZE | |
/dev/nvhost-as-gpu | Inout | 64 | 0xC0404108 | #NVGPU_AS_IOCTL_GET_VA_REGIONS | |
/dev/nvhost-as-gpu | In | 40 | 0x40284109 | #NVGPU_AS_IOCTL_INITIALIZE_EX | |
/dev/nvhost-as-gpu | Inout | 20 | 0xC0144114 |
NVGPU_AS_IOCTL_BIND_CHANNEL
Identical to Linux driver.
struct { u32 __fd; // in };
NVGPU_AS_IOCTL_ALLOC_SPACE
This one reserves pages in the device address space.
struct { u32 __pages; // in u32 __page_size; // in u32 __flags; // in u32 __pad; union { u64 __offset; // out u64 __align; // in }; };
NVGPU_AS_IOCTL_FREE_SPACE
struct { u64 __offset; // in u32 __pages; // in u32 __page_size; // in };
NVGPU_AS_IOCTL_MAP_BUFFER
Map a memory region in the device address space. Identical to Linux driver pretty much.
On success, the mapped memory region is locked by having SVC#MemoryState bit34 set.
struct { u32 __flags; // in, 4 works u32 __reserved; u32 __nvmap_handle; // in u32 __page_size; // inout, 0 means don't care union { u64 __offset; // out u64 __align; // in }; };
NVGPU_AS_IOCTL_UNMAP_BUFFER
Doesn't do shit.
NVGPU_AS_IOCTL_INITIALIZE
Nintendo custom.
struct { u32 __size; // in (must be aligned to 0x10000; 0=default) u32 __zeroes[3]; // in };
NVGPU_AS_IOCTL_GET_VA_REGIONS
Nintendo modified to get rid of pointer in struct.
struct va_region { u64 __offset; u32 __page_size; u32 __reserved; u64 __pages; }; struct { u64 __not_used; // (contained output user ptr on linux, ignored) u32 __bufsize; // inout, forced to 2*sizeof(struct va_region) u32 __reserved; struct va_region __regions[2]; // out };
NVGPU_AS_IOCTL_INITIALIZE_EX
Nintendo custom.
struct { u32 __size; // in (must be aligned to 0x10000; 0=default) u32 __pad0; u32 __unk0; // in u32 __pad1; u64 __unk1; // in u64 __unk2; // in u64 __unk3; // in };
/dev/nvmap
Value | Direction | Size | Description | Notes |
---|---|---|---|---|
0xC0080101 | Inout | 8 | #NVMAP_IOC_CREATE | |
0x00000102 | - | 0 | NVMAP_IOC_CLAIM | Returns NotSupported |
0xC0080103 | Inout | 8 | #NVMAP_IOC_FROM_ID | |
0xC0200104 | Inout | 32 | #NVMAP_IOC_ALLOC | |
0xC0180105 | Inout | 24 | #NVMAP_IOC_FREE | |
0xC0280106 | Inout | 40 | NVMAP_IOC_MMAP | Returns NotSupported |
0xC0280107 | Inout | 40 | NVMAP_IOC_WRITE | Returns NotSupported |
0xC0280108 | Inout | 40 | NVMAP_IOC_READ | Returns NotSupported |
0xC00C0109 | Inout | 12 | #NVMAP_IOC_PARAM | |
0xC010010A | Inout | 16 | NVMAP_IOC_PIN_MULT | Returns NotSupported |
0xC010010B | Inout | 16 | NVMAP_IOC_UNPIN_MULT | Returns NotSupported |
0xC008010C | Inout | 8 | NVMAP_IOC_CACHE | Returns NotSupported |
0xC004010D | Inout | 4 | Returns NotSupported | |
0xC008010E | Inout | 8 | #NVMAP_IOC_GET_ID | |
0xC004010F | Inout | 4 | Returns NotSupported | |
0x40040110 | In | 4 | Returns NotSupported | |
0x00000111 | - | 0 | Returns NotSupported |
NVMAP_IOC_CREATE
Creates an nvmap object. Identical to Linux driver.
struct { u32 __size; // in u32 __handle; // out };
NVMAP_IOC_FROM_ID
Get handle to an existing nvmap object. Identical to Linux driver.
struct { u32 __id; // in u32 __handle; // out };
NVMAP_IOC_ALLOC
Allocate memory for the nvmap object. Nintendo extended this one with 16 bytes, and changed it from in to inout.
struct { u32 __handle; // in u32 __heapmask; // in u32 __flags; // in (0=read-only, 1=read-write) u32 __align; // in u8 __unk0; // in u8 __pad[7]; u64 __addr; // in };
NVMAP_IOC_FREE
This one is completely custom. Partly because the Linux driver passed the handle as the ioctl "arg-ptr", and HIPC can't handle that voodoo.
struct { u32 __handle; // in u32 __pad; u64 __refcount; // out u32 __size; // out u32 __flags; // out, 1=NOT_FREED_YET };
NVMAP_IOC_PARAM
Returns info about a nvmap object. Identical to Linux driver, but extended with further params.
struct { u32 __handle; // in u32 __param; // in, 1=SIZE, 2=ALIGNMENT, 3=BASE (returns error), 4=HEAP (always 0x40000000), 5=KIND, 6=COMPR (unused) u32 __result; // out };
NVMAP_IOC_GET_ID
Returns an id for a nvmap object. Identical to Linux driver.
struct { u32 __id; // out u32 __handle; // in };
/dev/nvhost-ctrl-gpu
This device is for global (context independent) operations on the gpu.
Value | Direction | Size | Description | Notes |
---|---|---|---|---|
0x80044701 | Out | 4 | NVGPU_GPU_IOCTL_ZCULL_GET_CTX_SIZE | |
0x80284702 | Out | 40 | NVGPU_GPU_IOCTL_ZCULL_GET_INFO | |
0x402C4703 | In | 44 | NVGPU_GPU_IOCTL_ZBC_SET_TABLE | |
0xC0344704 | Inout | 52 | NVGPU_GPU_IOCTL_ZBC_QUERY_TABLE | |
0xC0B04705 | Inout | 176 | NVGPU_GPU_IOCTL_GET_CHARACTERISTICS | |
0xC0184706 | Inout | 24 | NVGPU_GPU_IOCTL_GET_TPC_MASKS | |
0x40084707 | In | 8 | NVGPU_GPU_IOCTL_OPEN_CHANNEL | |
0x4008470E | In | 8 | ||
0x4010470F | In | 16 | ||
0xC0084710 | Inout | 8 | ||
0x80084711 | Out | 8 | ||
0x80084712 | Out | 8 | ||
0xC0044713 | Inout | 4 | ||
0x80084714 | Out | 8 | ||
0x80044715 | Out | 4 | ||
0x8018471A | Out | 24 | ||
0xC008471B | Inout | 8 | ||
0xC010471C | Inout | 16 |
Channels
Channels are a concept for NVIDIA hardware blocks that share a common interface.
Path | Name |
---|---|
/dev/nvhost-gpu | |
/dev/nvhost-vic | |
/dev/nvhost-nvdec | |
/dev/nvhost-nvjpg |
Channel Ioctls
Value | Size | Description | Notes |
---|---|---|---|
0xC0??0001 | Variable | NVHOST_IOCTL_CHANNEL_SUBMIT | |
0xC0080002 | 8 | NVHOST_IOCTL_CHANNEL_GET_SYNCPOINT | |
0xC0080003 | 8 | NVHOST_IOCTL_CHANNEL_GET_WAITBASE | |
0xC0080004 | 8 | NVHOST_IOCTL_CHANNEL_SET_TIMEOUT_EX | |
0x40040007 | 4 | ||
0xC0??0009 | Variable | NVHOST_IOCTL_CHANNEL_MAP_BUFFER | |
0xC0??000A | Variable | NVHOST_IOCTL_CHANNEL_UNMAP_BUFFER | |
0x00000013 | 0 | ||
0x40044801 | 4 | #NVGPU_IOCTL_CHANNEL_SET_NVMAP_FD | |
0x40044803 | 4 | NVGPU_IOCTL_CHANNEL_SET_PRIORITY | |
0x40084805 | 8 | #NVGPU_IOCTL_CHANNEL_ALLOC_GPFIFO | |
0xC0044807 | 4 | NVGPU_IOCTL_CHANNEL_CYCLE_STATS | |
0xC0??4808 | Variable | #NVGPU_IOCTL_CHANNEL_SUBMIT_GPFIFO | |
0xC0104809 | 16 | #NVGPU_IOCTL_CHANNEL_ALLOC_OBJ_CTX | |
0xC010480B | 16 | NVGPU_IOCTL_CHANNEL_ZCULL_BIND | |
0xC018480C | 24 | #NVGPU_IOCTL_CHANNEL_SET_ERROR_NOTIFIER | |
0x4004480D | 4 | #NVGPU_IOCTL_CHANNEL_OPEN | |
0x0000480E | 0 | #NVGPU_IOCTL_CHANNEL_ENABLE | |
0x0000480F | 0 | #NVGPU_IOCTL_CHANNEL_DISABLE | |
0x00004810 | 0 | #NVGPU_IOCTL_CHANNEL_PREEMPT | |
0x00004811 | 0 | #NVGPU_IOCTL_CHANNEL_FORCE_RESET | |
0x40084812 | 8 | #NVGPU_IOCTL_CHANNEL_EVENTS_CTRL | |
0xC0104813 | 16 | NVGPU_IOCTL_CHANNEL_CYCLE_STATS_SNAPSHOT | |
0x80804816 | 128 | Only works when the channel is busy | |
0xC0104817 | 16 | #NVGPU_IOCTL_CHANNEL_GET_ERROR | |
0x40204818 | 32 | #NVGPU_IOCTL_CHANNEL_ALLOC_GPFIFO_EX | |
0xC0??4819 | Variable | #NVGPU_IOCTL_CHANNEL_SUBMIT_GPFIFO_EX | |
0xC020481A | 32 | #NVGPU_IOCTL_CHANNEL_ALLOC_GPFIFO_EX2 | |
0x40084714 | 8 | set_user_address | Sets an unknown user context address |
0x80084715 | 8 | get_user_address | Gets an unknown user context address |
NVGPU_IOCTL_CHANNEL_SET_NVMAP_FD
Binds a nvmap object to this channel. Identical to Linux driver.
struct { u32 __nvmap_fd; // in };
NVGPU_IOCTL_CHANNEL_ALLOC_GPFIFO
Allocates gpfifo entries. Identical to Linux driver.
struct { u32 __num_entries; // in u32 __flags; // in };
NVGPU_IOCTL_CHANNEL_SUBMIT_GPFIFO
Submits a gpfifo object. Modified to take inline entry objects instead of a pointer.
struct fence { u32 __id; u32 __value; }; struct gpfifo_entry { u32 __entry0; u32 __entry1; }; struct { u64 __gpfifo; // in (pointer to gpfifo fence structs; ignored) u32 __num_entries; // in (number of fence objects being submitted) u32 __flags; // in struct fence __fence_out; // out (returned new fence object for others to wait on) struct gpfifo_entry __entries[]; // in (depends on __num_entries) };
NVGPU_IOCTL_CHANNEL_ALLOC_OBJ_CTX
Allocates a graphics context object. Modified to ignore object's ID.
struct { u32 __class_num; // in (0xB197=2d, 0xB1C0=compute, 0xA140=kepler, 0xB0B5=DMA, 0xB06F=channel_gpfifo) u32 __flags; // in u64 __obj_id; // out (ignored; used for FREE_OBJ_CTX ioctl, which is not supported) };
NVGPU_IOCTL_CHANNEL_SET_ERROR_NOTIFIER
Initializes the error notifier for this channel. Identical to Linux driver.
struct { u64 __offset; // in u64 __size; // in u32 __mem; // in (nvmap object handle) u32 __padding; // in };
NVGPU_IOCTL_CHANNEL_OPEN
Opens the current channel. Unused and takes an unknown argument.
struct { u32 __unk; // in (only accepts 0x32, 0x64 or 0x96) };
NVGPU_IOCTL_CHANNEL_ENABLE
Enables the current channel. Identical to Linux driver.
NVGPU_IOCTL_CHANNEL_DISABLE
Disables the current channel. Identical to Linux driver.
NVGPU_IOCTL_CHANNEL_PREEMPT
Clears the FIFO pipe for this channel. Identical to Linux driver.
NVGPU_IOCTL_CHANNEL_FORCE_RESET
Forces the channel to reset. Identical to Linux driver.
NVGPU_IOCTL_CHANNEL_EVENTS_CTRL
Controls event notifications. Modified to take an additional argument.
struct { u32 __cmd; // in (0=disable, 1=enable, 2=clear) u32 __unk; // in (accepts 1 or 2) };
NVGPU_IOCTL_CHANNEL_GET_ERROR
Returns the current error notification caught by the error notifier. Exclusive to the Switch.
struct { u64 __timestamp; // out (nanoseconds since Jan. 1, 1970) u32 __info32; // out (error code) u16 __info16; // out (additional error info) u16 __status; // out (always 0xFFFF) };
NVGPU_IOCTL_CHANNEL_ALLOC_GPFIFO_EX
Allocates gpfifo entries with additional parameters. Exclusive to the Switch.
struct { u32 __num_entries; // in u32 __flags; // in u32 __unk0; // in (1 works) u32 __unk1; // in u32 __unk2; // in u32 __unk3; // in u32 __unk4; // in u32 __unk5; // in };
NVGPU_IOCTL_CHANNEL_SUBMIT_GPFIFO_EX
Submits a gpfifo object (async version). Exclusive to the Switch.
struct { u64 __gpfifo; // in (pointer to gpfifo fence structs; ignored) u32 __num_entries; // in (number of fence objects being submitted) u32 __flags; // in struct fence __fence_out; // out (returned new fence object for others to wait on) struct gpfifo_entry __entries[]; // in (depends on __num_entries) };
NVGPU_IOCTL_CHANNEL_ALLOC_GPFIFO_EX2
Allocates gpfifo entries with additional parameters and returns a fence. Exclusive to the Switch.
struct { u32 __num_entries; // in u32 __flags; // in u32 __unk0; // in (1 works) struct fence __fence_out; // out u32 __unk1; // in u32 __unk2; // in u32 __unk3; // in };
Remaining Ioctls
Value | Size | Description | Notes |
---|---|---|---|
/dev/nvhost-dbg-gpu | 0x40084401 | NVGPU_DBG_GPU_IOCTL_BIND_CHANNEL | |
/dev/nvhost-dbg-gpu | 0xC0??4402 | NVGPU_DBG_GPU_IOCTL_REG_OPS | ?? == size is unknown |
/dev/nvhost-dbg-gpu | 0x40084403 | NVGPU_DBG_GPU_IOCTL_EVENTS_CTRL | |
/dev/nvhost-dbg-gpu | 0x40044404 | NVGPU_DBG_GPU_IOCTL_POWERGATE | |
/dev/nvhost-dbg-gpu | 0x40044405 | NVGPU_DBG_GPU_IOCTL_SMPC_CTXSW_MODE | |
/dev/nvhost-dbg-gpu | 0xC0184407 | NVGPU_DBG_GPU_IOCTL_PERFBUF_MAP | |
/dev/nvhost-dbg-gpu | 0x40084408 | NVGPU_DBG_GPU_IOCTL_PERFBUF_UNMAP | |
/dev/nvhost-dbg-gpu | 0x40084409 | NVGPU_DBG_GPU_IOCTL_PC_SAMPLING |
nvmemp
NVIDIA memory profiler (this service is not available on retail units).
mm:u
NVIDIA multimedia (NvMM) platform service.
Cmd | Name |
---|---|
0 | ? |
1 | ? |
2 | ? |
3 | ? |
4 | module_init_clk |
5 | module_deinit_clk |
6 | module_set_clk_rate |
7 | module_get_clk_rate |
Errors
Most nvidia driver commands return an error code apart from the normal return code.
Cmd | Name |
---|---|
0 | Success |
1 | NotImplemented |
2 | NotSupported |
3 | NotInitialized |
4 | BadParameter |
5 | Timeout |
6 | InsufficientMemory |
7 | ReadOnlyAttribute |
8 | InvalidState |
9 | InvalidAddress |
0xA | InvalidSize |
0xB | BadValue |
0xD | AlreadyAllocated |
0xE | Busy |
0xF | ResourceError |
0x10 | CountMismatch |
0x1000 | SharedMemoryTooSmall |
0x30003 | FileOperationFailed |
0x3000F | IoctlFailed |