STRUCT NTB_DEV_OPS(9)
π struct ntb_dev_ops(9) π
okay so this is from the Kernel API Manual, section 9, and it's literally the blueprint for how an NTB device (that's Non-Transparent Bridge, iykyk) does its thing. it's a big ol' struct full of function pointers and bestie, there are so many of them. buckle up. π
β¨ NAME β¨
struct ntb_dev_ops β ntb device operations. that's the whole vibe. it's the ops table. the main character of the NTB world. π
π¦ SYNOPSIS π¦
here's the whole struct, no cap, every single pointer, exactly as it lives:
struct ntb_dev_ops {
int (*port_number)(struct ntb_dev *ntb);
int (*peer_port_count)(struct ntb_dev *ntb);
int (*peer_port_number)(struct ntb_dev *ntb, int pidx);
int (*peer_port_idx)(struct ntb_dev *ntb, int port);
u64 (*link_is_up)(struct ntb_dev *ntb, enum ntb_speed *speed, enum
ntb_width *width);
int (*link_enable)(struct ntb_dev *ntb, enum ntb_speed max_speed,
enum ntb_width max_width);
int (*link_disable)(struct ntb_dev *ntb);
int (*mw_count)(struct ntb_dev *ntb, int pidx);
int (*mw_get_align)(struct ntb_dev *ntb, int pidx, int widx,
resource_size_t *addr_align, resource_size_t *size_align,
resource_size_t *size_max);
int (*mw_set_trans)(struct ntb_dev *ntb, int pidx, int widx,
dma_addr_t addr, resource_size_t size);
int (*mw_clear_trans)(struct ntb_dev *ntb, int pidx, int widx);
int (*peer_mw_count)(struct ntb_dev *ntb);
int (*peer_mw_get_addr)(struct ntb_dev *ntb, int widx, phys_addr_t
*base, resource_size_t *size);
int (*peer_mw_set_trans)(struct ntb_dev *ntb, int pidx, int widx,
u64 addr, resource_size_t size);
int (*peer_mw_clear_trans)(struct ntb_dev *ntb, int pidx, int widx);
int (*db_is_unsafe)(struct ntb_dev *ntb);
u64 (*db_valid_mask)(struct ntb_dev *ntb);
int (*db_vector_count)(struct ntb_dev *ntb);
u64 (*db_vector_mask)(struct ntb_dev *ntb, int db_vector);
u64 (*db_read)(struct ntb_dev *ntb);
int (*db_set)(struct ntb_dev *ntb, u64 db_bits);
int (*db_clear)(struct ntb_dev *ntb, u64 db_bits);
u64 (*db_read_mask)(struct ntb_dev *ntb);
int (*db_set_mask)(struct ntb_dev *ntb, u64 db_bits);
int (*db_clear_mask)(struct ntb_dev *ntb, u64 db_bits);
int (*peer_db_addr)(struct ntb_dev *ntb, phys_addr_t *db_addr,
resource_size_t *db_size, u64 *db_data, int db_bit);
u64 (*peer_db_read)(struct ntb_dev *ntb);
int (*peer_db_set)(struct ntb_dev *ntb, u64 db_bits);
int (*peer_db_clear)(struct ntb_dev *ntb, u64 db_bits);
u64 (*peer_db_read_mask)(struct ntb_dev *ntb);
int (*peer_db_set_mask)(struct ntb_dev *ntb, u64 db_bits);
int (*peer_db_clear_mask)(struct ntb_dev *ntb, u64 db_bits);
int (*spad_is_unsafe)(struct ntb_dev *ntb);
int (*spad_count)(struct ntb_dev *ntb);
u32 (*spad_read)(struct ntb_dev *ntb, int sidx);
int (*spad_write)(struct ntb_dev *ntb, int sidx, u32 val);
int (*peer_spad_addr)(struct ntb_dev *ntb, int pidx, int sidx,
phys_addr_t *spad_addr);
u32 (*peer_spad_read)(struct ntb_dev *ntb, int pidx, int sidx);
int (*peer_spad_write)(struct ntb_dev *ntb, int pidx, int sidx, u32
val);
int (*msg_count)(struct ntb_dev *ntb);
u64 (*msg_inbits)(struct ntb_dev *ntb);
u64 (*msg_outbits)(struct ntb_dev *ntb);
u64 (*msg_read_sts)(struct ntb_dev *ntb);
int (*msg_clear_sts)(struct ntb_dev *ntb, u64 sts_bits);
int (*msg_set_mask)(struct ntb_dev *ntb, u64 mask_bits);
int (*msg_clear_mask)(struct ntb_dev *ntb, u64 mask_bits);
u32 (*msg_read)(struct ntb_dev *ntb, int *pidx, int midx);
int (*peer_msg_write)(struct ntb_dev *ntb, int pidx, int midx, u32
msg);
struct device *(*get_dma_dev)(struct ntb_dev *ntb);
};
it's giving "wall of function pointers" and honestly? iconic. π
πΈ Members πΈ
okay so every single member, and what it points at. and the answer is basically "go read the other page" for all of them β that's not me being lazy, that's literally what the man page says. I'm just the messenger. π«Ά
port_numberβ Seentb_port_number.peer_port_countβ Seentb_peer_port_count.peer_port_numberβ Seentb_peer_port_number.peer_port_idxβ Seentb_peer_port_idx.link_is_upβ Seentb_link_is_up.link_enableβ Seentb_link_enable.link_disableβ Seentb_link_disable.mw_countβ Seentb_mw_count.mw_get_alignβ Seentb_mw_get_align.mw_set_transβ Seentb_mw_set_trans.mw_clear_transβ Seentb_mw_clear_trans.peer_mw_countβ Seentb_peer_mw_count.peer_mw_get_addrβ Seentb_peer_mw_get_addr.peer_mw_set_transβ Seentb_peer_mw_set_trans.peer_mw_clear_transβ Seentb_peer_mw_clear_trans.db_is_unsafeβ Seentb_db_is_unsafe.db_valid_maskβ Seentb_db_valid_mask.db_vector_countβ Seentb_db_vector_count.db_vector_maskβ Seentb_db_vector_mask.db_readβ Seentb_db_read.db_setβ Seentb_db_set.db_clearβ Seentb_db_clear.db_read_maskβ Seentb_db_read_mask.db_set_maskβ Seentb_db_set_mask.db_clear_maskβ Seentb_db_clear_mask.peer_db_addrβ Seentb_peer_db_addr.peer_db_readβ Seentb_peer_db_read.peer_db_setβ Seentb_peer_db_set.peer_db_clearβ Seentb_peer_db_clear.peer_db_read_maskβ Seentb_peer_db_read_mask.peer_db_set_maskβ Seentb_peer_db_set_mask.peer_db_clear_maskβ Seentb_peer_db_clear_mask.spad_is_unsafeβ Seentb_spad_is_unsafe.spad_countβ Seentb_spad_count.spad_readβ Seentb_spad_read.spad_writeβ Seentb_spad_write.peer_spad_addrβ Seentb_peer_spad_addr.peer_spad_readβ Seentb_peer_spad_read.peer_spad_writeβ Seentb_peer_spad_write.msg_countβ Seentb_msg_count.msg_inbitsβ Seentb_msg_inbits.msg_outbitsβ Seentb_msg_outbits.msg_read_stsβ Seentb_msg_read_sts.msg_clear_stsβ Seentb_msg_clear_sts.msg_set_maskβ Seentb_msg_set_mask.msg_clear_maskβ Seentb_msg_clear_mask.msg_readβ Seentb_msg_read.peer_msg_writeβ Seentb_peer_msg_write.get_dma_devβ Seentb_get_dma_dev.
likeβ¦ every single one is a redirect. it's a struct of "please see also". the way that this struct is basically a table of contents? obsessed. π
π₯ SEE ALSO π₯
bestie there are so many friends. the whole kernel family showed up. also pls note the kernel file: Kernel file ./include/linux/ntb.h
the enums and structs first, because they're the β¨foundationβ¨:
enum ntb_topo(9),enum ntb_speed(9),enum ntb_width(9),enum ntb_default_port(9)struct ntb_client_ops(9),struct ntb_ctx_ops(9),struct ntb_client(9),struct ntb_dev(9)
then the register/unregister + context + event girlies:
ntb_register_client(9),ntb_unregister_client(9),ntb_register_device(9),ntb_unregister_device(9)ntb_set_ctx(9),ntb_clear_ctx(9),ntb_link_event(9),ntb_db_event(9),ntb_msg_event(9)
the port number crew (defaults + real ones):
ntb_default_port_number(9),ntb_default_peer_port_count(9),ntb_default_peer_port_number(9),ntb_default_peer_port_idx(9)ntb_port_number(9),ntb_peer_port_count(9),ntb_peer_port_number(9),ntb_logical_port_number(9),ntb_peer_logical_port_number(9),ntb_peer_port_idx(9)
the link squad:
the memory window besties:
ntb_mw_count(9),ntb_mw_get_align(9),ntb_mw_set_trans(9),ntb_mw_clear_trans(9)ntb_peer_mw_count(9),ntb_peer_mw_get_addr(9),ntb_peer_mw_set_trans(9),ntb_peer_mw_clear_trans(9)
the doorbell section (it's long, it's loud, it's slaying):
ntb_db_is_unsafe(9),ntb_db_valid_mask(9),ntb_db_vector_count(9),ntb_db_vector_mask(9)ntb_db_read(9),ntb_db_set(9),ntb_db_clear(9),ntb_db_read_mask(9),ntb_db_set_mask(9),ntb_db_clear_mask(9)ntb_peer_db_addr(9),ntb_peer_db_read(9),ntb_peer_db_set(9),ntb_peer_db_clear(9),ntb_peer_db_read_mask(9),ntb_peer_db_set_mask(9),ntb_peer_db_clear_mask(9)
the scratchpad squad:
ntb_spad_is_unsafe(9),ntb_spad_count(9),ntb_spad_read(9),ntb_spad_write(9)ntb_peer_spad_addr(9),ntb_peer_spad_read(9),ntb_peer_spad_write(9)
the messaging crew:
ntb_msg_count(9),ntb_msg_inbits(9),ntb_msg_outbits(9),ntb_msg_read_sts(9),ntb_msg_clear_sts(9),ntb_msg_set_mask(9),ntb_msg_clear_mask(9),ntb_msg_read(9),ntb_peer_msg_write(9)
and the last three, saving the finale for the end:
fr fr that's the whole page. 49 member redirects and 77 see-alsos later, you're basically an NTB expert. go read the friends next, they've got the actual tea. π
and that's a wrap bestie!! this page lives in ./include/linux and the version notes say October 2026 β so yes, it's giving future-iconic. go forth and slay those function pointers. πβ¨π
π¦ where this page comes from
- nixpkgs unstable: linux-manual 7.3.1
- π girlified by deepseek-ai/DeepSeek-V4.1-Flash-1017 on : a language model's rewrite of the original, under its terms