drivers/crypto/hisilicon/sgl.c
Source file repositories/reference/linux-study-clean/drivers/crypto/hisilicon/sgl.c
File Facts
- System
- Linux kernel
- Corpus path
drivers/crypto/hisilicon/sgl.c- Extension
.c- Size
- 7583 bytes
- Lines
- 291
- Domain
- Driver Families
- Bucket
- drivers/crypto
- Inferred role
- Driver Families: exported/initcall integration point
- Status
- integration implementation candidate
Why This File Exists
Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Exports symbols or registers init work; inspect boot/module ordering and who consumes the exported contract.
- Touches IRQ or DMA behavior; this matters for the representative real-device path.
- Allocates kernel memory; connect allocation flags and lifetime to context constraints.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/align.hlinux/dma-mapping.hlinux/hisi_acc_qm.hlinux/module.hlinux/slab.h
Detected Declarations
struct acc_hw_sgestruct hisi_acc_hw_sglstruct hisi_acc_sgl_poolstruct mem_blockfunction hisi_acc_create_sgl_poolfunction hisi_acc_free_sgl_poolfunction sg_map_to_hw_sgfunction inc_hw_sgl_sgefunction update_hw_sgl_sum_sgefunction clear_hw_sgl_sgefunction hisi_acc_sg_buf_map_to_hw_sglfunction for_each_sgfunction hisi_acc_sg_buf_unmapexport hisi_acc_create_sgl_poolexport hisi_acc_free_sgl_poolexport hisi_acc_sg_buf_map_to_hw_sglexport hisi_acc_sg_buf_unmap
Annotated Snippet
struct acc_hw_sge {
dma_addr_t buf;
void *page_ctrl;
__le32 len;
__le32 pad;
__le32 pad0;
__le32 pad1;
};
/* use default sgl head size 64B */
struct hisi_acc_hw_sgl {
dma_addr_t next_dma;
__le16 entry_sum_in_chain;
__le16 entry_sum_in_sgl;
__le16 entry_length_in_sgl;
__le16 pad0;
__le64 pad1[5];
struct hisi_acc_hw_sgl *next;
struct acc_hw_sge sge_entries[];
} __aligned(1);
struct hisi_acc_sgl_pool {
struct mem_block {
struct hisi_acc_hw_sgl *sgl;
dma_addr_t sgl_dma;
size_t size;
} mem_block[HISI_ACC_MEM_BLOCK_NR];
u32 sgl_num_per_block;
u32 block_num;
u32 count;
u32 sge_nr;
size_t sgl_size;
};
/**
* hisi_acc_create_sgl_pool() - Create a hw sgl pool.
* @dev: The device which hw sgl pool belongs to.
* @count: Count of hisi_acc_hw_sgl in pool.
* @sge_nr: The count of sge in hw_sgl
*
* This function creates a hw sgl pool, after this user can get hw sgl memory
* from it.
*/
struct hisi_acc_sgl_pool *hisi_acc_create_sgl_pool(struct device *dev,
u32 count, u32 sge_nr)
{
u32 sgl_size, block_size, sgl_num_per_block, block_num, remain_sgl;
struct hisi_acc_sgl_pool *pool;
struct mem_block *block;
u32 i, j;
if (!dev || !count || !sge_nr || sge_nr > HISI_ACC_SGL_SGE_NR_MAX)
return ERR_PTR(-EINVAL);
sgl_size = ALIGN(sizeof(struct acc_hw_sge) * sge_nr +
sizeof(struct hisi_acc_hw_sgl),
HISI_ACC_SGL_ALIGN_SIZE);
/*
* the pool may allocate a block of memory of size PAGE_SIZE * 2^MAX_PAGE_ORDER,
* block size may exceed 2^31 on ia64, so the max of block size is 2^31
*/
block_size = 1 << (PAGE_SHIFT + MAX_PAGE_ORDER < 32 ?
PAGE_SHIFT + MAX_PAGE_ORDER : 31);
sgl_num_per_block = block_size / sgl_size;
block_num = count / sgl_num_per_block;
remain_sgl = count % sgl_num_per_block;
if ((!remain_sgl && block_num > HISI_ACC_MEM_BLOCK_NR) ||
(remain_sgl > 0 && block_num > HISI_ACC_MEM_BLOCK_NR - 1))
return ERR_PTR(-EINVAL);
pool = kzalloc_obj(*pool);
if (!pool)
return ERR_PTR(-ENOMEM);
block = pool->mem_block;
for (i = 0; i < block_num; i++) {
block[i].sgl = dma_alloc_coherent(dev, block_size,
&block[i].sgl_dma,
GFP_KERNEL);
if (!block[i].sgl) {
dev_err(dev, "Fail to allocate hw SG buffer!\n");
goto err_free_mem;
}
block[i].size = block_size;
}
if (remain_sgl > 0) {
Annotation
- Immediate include surface: `linux/align.h`, `linux/dma-mapping.h`, `linux/hisi_acc_qm.h`, `linux/module.h`, `linux/slab.h`.
- Detected declarations: `struct acc_hw_sge`, `struct hisi_acc_hw_sgl`, `struct hisi_acc_sgl_pool`, `struct mem_block`, `function hisi_acc_create_sgl_pool`, `function hisi_acc_free_sgl_pool`, `function sg_map_to_hw_sg`, `function inc_hw_sgl_sge`, `function update_hw_sgl_sum_sge`, `function clear_hw_sgl_sge`.
- Atlas domain: Driver Families / drivers/crypto.
- Implementation status: integration implementation candidate.
- IRQ or DMA behavior appears here, which is relevant to the selected PCIe/NVMe device path.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.