Skip to content

Commit 694ce9a

Browse files
committed
npu:phytium Add the driver for Phytium NPU engine
This patch adds the NPU driver, which will driver the neural network processing unit. You can use this driver to do picture classification and intelligent recognition, it will be a good AI module. Signed-off-by: yuanxia <[email protected]> Signed-off-by: Cheng Quan <[email protected]> Signed-off-by: Wang Yinfeng <[email protected]>
1 parent 4adaf90 commit 694ce9a

20 files changed

+4836
-0
lines changed

drivers/staging/Kconfig

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -80,4 +80,5 @@ source "drivers/staging/qlge/Kconfig"
8080

8181
source "drivers/staging/vme_user/Kconfig"
8282

83+
source "drivers/staging/phytium-npu/Kconfig"
8384
endif # STAGING

drivers/staging/Makefile

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,3 +29,4 @@ obj-$(CONFIG_PI433) += pi433/
2929
obj-$(CONFIG_XIL_AXIS_FIFO) += axis-fifo/
3030
obj-$(CONFIG_FIELDBUS_DEV) += fieldbus/
3131
obj-$(CONFIG_QLGE) += qlge/
32+
obj-$(CONFIG_PHYTIUM_NPU) += phytium-npu/

drivers/staging/phytium-npu/Kconfig

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
# SPDX-License-Identifier: GPL-2.0
2+
menuconfig PHYTIUM_NPU
3+
tristate "Phytium neural network processing unit"
4+
depends on ARCH_PHYTIUM
5+
help
6+
Say Y here if your want support for Phytium NPU controller framework.
7+
This is common support for devices that embed the Phytium NPU IP.
8+
9+
To compile this driver as a module, choose M here: the module will be
10+
called phytium_npu.
11+
12+
if PHYTIUM_NPU
13+
choice
14+
prompt "Select the Phytium NPU Hardware"
15+
default y
16+
help
17+
You need to select a suitable NPU controller in the current board.
18+
This option allows you to decide which Phytium NPU will be built
19+
in system.
20+
If in doubt, select 'N'
21+
config NPU_PLATFORM
22+
tristate "driver runs on platform"
23+
help
24+
Say Y here if you want to support for IO Mapped Phytium NPU controller.
25+
This support is for devices that have the Phytium NPU controller IP.
26+
To compile this driver as a module, choose M here: the module will be
27+
called phytium_npu_platform.
28+
config NPU_PCI
29+
tristate "driver runs on PCI hardware"
30+
help
31+
Say Y here if you want to support for Phytium NPU controller connected
32+
to the PCI bus. This support is for devices that have the Phytium NPU
33+
controller IP embedded into a PCI device.
34+
To compile this driver as a module, choose M here: the module will be
35+
called phytium_npu_pci.
36+
endchoice
37+
endif

drivers/staging/phytium-npu/Makefile

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
# SPDX-License-Identifier: GPL-2.0
2+
ccflags-y += -I$(src)/include/
3+
4+
ifdef CONFIG_NPU_PLATFORM
5+
ifeq ($(CONFIG_NPU_PLATFORM),m)
6+
EXTRA_CFLAGS += -DPHYTIUM_NPU_PLATFORM
7+
endif
8+
9+
ifeq ($(CONFIG_NPU_PLATFORM),y)
10+
EXTRA_CFLAGS += -DPHYTIUM_NPU_PLATFORM
11+
endif
12+
endif
13+
14+
obj-$(CONFIG_PHYTIUM_NPU) += phytium_npu.o
15+
phytium_npu-y := phytium_npu_common.o phytium_npu_dev.o \
16+
phytium_npu_dev_mmu.o phytium_npu_mm_mmu.o phytium_npu_workqueue.o \
17+
phytium_npu_session.o phytium_npu_uapi.o phytium_npu_debug.o
18+
19+
obj-$(CONFIG_NPU_PLATFORM) += phytium_npu_platform.o
20+
obj-$(CONFIG_NPU_PCI) += phytium_npu_pci.o
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
# SPDX-License-Identifier: GPL-2.0
2+
export CONFIG_PHYTIUM_NPU := y
3+
export CONFIG_NPU_PLATFORM := y
4+
export CONFIG_PHYTIUM_NPU_DMA_HEAP := y
5+
include Makefile
6+
ARCH := arm64
7+
CROSS_COMPILE := aarch64-linux-gnu-
8+
9+
#------------------------------------
10+
# for internal use
11+
#------------------------------------
12+
13+
ifeq ($(KERNELRELEASE),)
14+
15+
#KDIR ?= /lib/modules/$(shell uname -r)/build
16+
KSRC := /home/chengquan/code/phytium-linux-kernel-master/
17+
PWD := $(shell pwd)
18+
19+
# kernel warning levels: as high as possible:
20+
# W=12 and W=123 seem to warn about linux kernel headers, so use W=1.
21+
KWARN := W=1
22+
23+
ifneq (,$(shell which sparse))
24+
# C=1: use 'sparse' for extra warnings, if it is avail.
25+
SPARSE := C=1
26+
endif
27+
28+
all: modules
29+
modules:
30+
$(MAKE) ARCH=$(ARCH) CROSS_COMPILE=$(CROSS_COMPILE)-C $(KSRC) M=$(shell pwd) modules
31+
32+
clean:
33+
$(MAKE) -C $(KDIR) M=$(PWD) clean
34+
check:
35+
cd $(KDIR); scripts/checkpatch.pl -f `find $(PWD)/include -name "*\.[ch]"`
36+
37+
endif # KERNELRELEASE
Lines changed: 213 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,213 @@
1+
/* SPDX-License-Identifier: GPL */
2+
/*
3+
* Copyright (C) 2023 Phytium Technology Co., Ltd.
4+
*/
5+
#ifndef __PHYTIUM_NPU_H__
6+
#define __PHYTIUM_NPU_H__
7+
#include <linux/list.h>
8+
#include <linux/spinlock.h>
9+
#include <linux/miscdevice.h>
10+
#include <linux/iosys-map.h>
11+
#include "phytium_npu_mmu.h"
12+
13+
#define NPU_SUPPORT_SESSION_NUM 128
14+
#ifndef TRUE
15+
#define TRUE 1
16+
#endif
17+
#ifndef FALSE
18+
#define FALSE 0
19+
#endif
20+
21+
#define NPU_STREAM_NONE 0x0
22+
#define NPU_STREAM_IN_HW 0x1
23+
#define NPU_STREAM_SCHEDULED 0x09
24+
#define NPU_STREAM_BUFF_IN_HW 0x10
25+
#define NPU_STREAM_BUFF_NO_READY 0x11
26+
#define NPU_STREAM_BUFF_BUSY 0x12
27+
28+
#define NPU_STREAM_INFER_NONE 0x0
29+
#define NPU_STREAM_INFER_WAIT 0x2
30+
#define NPU_STREAM_INFER_WORK 0x3
31+
#define NPU_STREAM_INFER_DONE 0x4
32+
33+
#define NPU_MMU_CONTEXT_NUM 2
34+
#define NPU_MMU_CONTEXT_MODULE_ID 0
35+
#define NPU_MMU_CONTEXT_IO_ID 1
36+
37+
#define NEED_NOTHING 0x0
38+
#define NEED_SCHEDULE 0x1
39+
#define NEED_QUEUE_STREAM 0x2
40+
41+
#define NPU_AUTO_SUSPEND_TIMEOUT 5000
42+
#define NPU_ACPI_POWER_TYPE 0x1
43+
#define GET_TIME_NS(ts) ktime_get_real_ts64(ts)
44+
/* state of the NPU device: power up or down */
45+
enum npu_power_state {
46+
NPU_STATE_OFF,
47+
NPU_STATE_ON
48+
};
49+
50+
struct phytium_npu_stream;
51+
52+
struct phytium_npu_debugfs {
53+
u32 debug_mode; /* register|mem file */
54+
/* perf|band|crc|PB_stream|PB_layer|PB_pass|crc_stream|crc_layer|crc|pass */
55+
u32 debug_type;
56+
u32 debug_fd; /* debug perf or band memory fd */
57+
u32 debug_crc_fd; /* debug crc memory fd */
58+
u32 debug_size;
59+
u64 debug_addr;
60+
u64 debug_crc_addr;
61+
struct iosys_map debug_map;
62+
struct iosys_map debug_crc_map;
63+
struct dentry *sess_dbgfs_dir;
64+
};
65+
66+
struct phytium_npu_session {
67+
struct phytium_npu_dev *npu_dev;
68+
struct list_head sess_list_entry;
69+
struct list_head sched_list_entry;
70+
struct list_head stream_list;
71+
struct list_head response_list;
72+
struct list_head map_mmu_list;
73+
struct phytium_npu_mmu_context mmu_ctx[NPU_MMU_CONTEXT_NUM];
74+
struct npu_mmu_ctx *share_mctx; //mctx is belong to sesson
75+
struct phytium_npu_debugfs dbgfs;
76+
wait_queue_head_t response_wq;
77+
int id;
78+
};
79+
80+
struct phytium_npu_dev {
81+
struct platform_device *pdev;
82+
struct device *dev;
83+
struct miscdevice miscdev;
84+
struct list_head sessions_list;
85+
struct list_head sched_sess_list;
86+
struct dentry *dbgfs_root_dir;
87+
struct phytium_npu_stream *activated_stream; /* stream had work on hardware */
88+
struct phytium_npu_stream *queued_stream; /* stream wait for activate */
89+
struct workqueue_struct *stream_wq;
90+
struct work_struct stream_work;
91+
struct delayed_work rt_delay_work;
92+
struct npu_mmu_config_global nmmu_config;
93+
struct mutex mutex_lock; /* protect stream */
94+
spinlock_t spin_irq_lock; /* protect interrupt */
95+
int used_mmu_context_id[4];
96+
u32 irq_status;
97+
int sessions_count;
98+
int is_cache_stream_on;
99+
int is_use_repeat;
100+
int is_platform_dev;
101+
int irq;
102+
int power_status;
103+
int load_status;
104+
int voltage_val;
105+
int clock_freq;
106+
void __iomem *reg_base;
107+
void __iomem *power_reg_base;
108+
struct timespec64 ts;
109+
struct timespec64 te;
110+
struct timespec64 tspan;
111+
};
112+
113+
struct npu_user_stream_rsp {
114+
struct phytium_npu_session *session;
115+
struct list_head stream_rsp_list_entry;
116+
int rsp_size;
117+
struct npu_user_rsp ursp;
118+
};
119+
120+
struct phytium_npu_stream {
121+
struct phytium_npu_session *session;
122+
struct list_head stream_list_entry;
123+
struct npu_user_stream_rsp *rsp;
124+
int stream_status; /* NONE|IN HARDWARE */
125+
int infer_status; /* NONE|QUEUED|WORK|DONE */
126+
int user_repeat_count; /* REPEAT COUNT */
127+
int all_buf_ready; /* NONE|READY */
128+
int is_rollback; /* NONE|ROLLBACK */
129+
struct npu_user_submit_stream nustream;
130+
};
131+
132+
//extern shared function
133+
int phytium_npu_session_init(struct phytium_npu_dev *npu, struct phytium_npu_session *session);
134+
struct phytium_npu_session *phytium_npu_session_create(struct device *dev);
135+
int phytium_npu_register_dev(struct device *dev, void *plat_data, void __iomem *reg_base);
136+
int phytium_npu_register_misc(struct phytium_npu_dev *npudev);
137+
int phytium_npu_unregister_misc(struct phytium_npu_dev *npudev);
138+
int phytium_npu_session_release(struct phytium_npu_dev *npu, struct phytium_npu_session *session);
139+
struct npu_mctx_map *phytium_npu_find_mmu_ctx_map(struct phytium_npu_session *sess, int dma_buf_fd);
140+
struct dma_buf *phytium_npu_check_and_get_dma_buf(struct phytium_npu_session *sess, int dma_buf_fd);
141+
struct phytium_npu_dev *phytium_npu_get_npudev(void);
142+
int phytium_npu_mmu_dev_init(struct phytium_npu_dev *npudev, int page_size);
143+
int phytium_npu_create_new_mmu_context(struct phytium_npu_dev *npu,
144+
struct phytium_npu_session *session);
145+
int phytium_npu_mmu_map_init(struct phytium_npu_dev *npu, struct phytium_npu_session *sess,
146+
struct npu_memory_map *usr_mmap);
147+
int phytium_npu_import_dmabuf(struct phytium_npu_dev *npu, struct phytium_npu_session *sess,
148+
struct npu_memory_map *usr_mmap);
149+
int phytium_npu_release_mmu_context(struct phytium_npu_dev *npu,
150+
struct phytium_npu_session *session);
151+
int phytium_npu_mmu_unmap(struct phytium_npu_dev *npu, struct phytium_npu_session *sess,
152+
struct npu_memory_unmap *usr_unmmap);
153+
void phytium_npu_mmu_output_status(struct phytium_npu_dev *npudev);
154+
int phytium_npu_mmu_config_dev_mmu(struct phytium_npu_session *sess);
155+
int phytium_npu_mmu_dev_flush_tlb(struct phytium_npu_dev *npudev, int ctxid);
156+
int phytium_npu_write_stream(struct phytium_npu_dev *npu, struct phytium_npu_session *sess,
157+
const char *stream_buf, size_t size);
158+
int phytium_npu_delete_stream(struct phytium_npu_dev *npu, struct phytium_npu_session *sess,
159+
struct npu_delete_stream *stream);
160+
int phytium_npu_handle_irq(struct device *dev);
161+
u32 phytium_npu_get_irq_status(struct phytium_npu_dev *npudev);
162+
u32 phytium_npu_get_irq_enable_status(struct phytium_npu_dev *npudev);
163+
void phytium_npu_clear_msi_irq(struct phytium_npu_dev *npudev);
164+
void phytium_npu_clear_irq_status(struct phytium_npu_dev *npudev, u32 event);
165+
void phytium_npu_config_preload(struct phytium_npu_dev *npudev);
166+
void phytium_npu_config_start_inference(struct phytium_npu_dev *npudev,
167+
struct phytium_npu_session *sess,
168+
struct phytium_npu_stream *nstream);
169+
int phytium_npu_handle_thread_irq(struct device *dev);
170+
int phytium_npu_hw_reset_self(struct phytium_npu_dev *npudev);
171+
void phytium_npu_config_hl_wdt(struct phytium_npu_dev *npudev);
172+
void phytium_npu_config_event(struct phytium_npu_dev *npudev, u32 events, int is_enable);
173+
u32 phytium_npu_get_axi_err_status(struct phytium_npu_dev *npudev);
174+
void phytium_npu_output_mem_wdt_err(struct phytium_npu_dev *npudev);
175+
void do_work(struct work_struct *work);
176+
void phytium_npu_schedule_stream_queues(struct phytium_npu_dev *npu, bool asynchronous);
177+
int phytium_npu_check_stream_buf_is_ready(struct phytium_npu_stream *nstream);
178+
void phytium_npu_set_stream_buf_status_with_fd(struct phytium_npu_session *sess,
179+
int fd, int status);
180+
void phytium_npu_repeat_stream(struct phytium_npu_session *sess, int stream_id, int is_repeat);
181+
182+
void phytium_npu_change_schedule_session(struct phytium_npu_session *sess,
183+
struct phytium_npu_dev *npu,
184+
int is_change);
185+
int phytium_npu_config_dma_address(struct phytium_npu_session *sess,
186+
struct phytium_npu_stream *nstream);
187+
void phytium_npu_config_clock(struct phytium_npu_dev *sess, int is_enable);
188+
int phytium_npu_submit_stream(struct phytium_npu_dev *npu, struct phytium_npu_session *sess,
189+
struct phytium_npu_stream *nstream);
190+
int phytium_npu_prepare_hw_4_queued_stream(struct phytium_npu_dev *npu,
191+
struct phytium_npu_session *sess,
192+
struct phytium_npu_stream *nstream);
193+
int phytium_npu_try_excute_queued_stream(struct phytium_npu_dev *npu);
194+
int phytium_npu_rollback_stream(struct phytium_npu_dev *npu);
195+
int phytium_npu_update_activated_stream_4_err_mmu(struct phytium_npu_dev *npu);
196+
int phytium_npu_session_release_all(struct phytium_npu_dev *npudev);
197+
int phytium_npu_unregister_dev(struct device *dev);
198+
int phytiun_npu_check_debug_fs_cfg(struct phytium_npu_session *sess);
199+
void phytium_npu_debug_set_hw_register(struct phytium_npu_dev *npu,
200+
struct phytium_npu_session *sess);
201+
void phytium_npu_debugfs_init(struct phytium_npu_dev *npu);
202+
void phytium_npu_debugfs_session_init(struct phytium_npu_dev *npu,
203+
struct phytium_npu_session *sess);
204+
void phytium_npu_debug_show_register(struct phytium_npu_dev *npu, struct phytium_npu_session *sess);
205+
void phytium_npu_debugfs_session_remove(struct phytium_npu_session *sess);
206+
void phytium_npu_debugfs_remove(struct phytium_npu_dev *npu);
207+
void phytium_npu_try_resume_work(struct phytium_npu_dev *npudev);
208+
int phytium_npu_schedule_suspend(struct phytium_npu_dev *npudev, u32 delay_ms);
209+
int phytium_npu_common_resume(struct device *dev);
210+
int phytium_npu_common_suspend(struct device *dev);
211+
void phytium_npu_get_time_span(struct timespec64 *start, struct timespec64 *end,
212+
struct timespec64 *span);
213+
#endif

0 commit comments

Comments
 (0)