* Copyright (c) Huawei Technologies Co., Ltd. 2025. All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 and
* only version 2 as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#include "ka_kernel_def_pub.h"
#include "ka_driver_pub.h"
#include "ka_fs_pub.h"
#include "devdrv_pci.h"
#include "devdrv_ctrl.h"
#include "devdrv_sysfs.h"
#include "devdrv_util.h"
#include "comm_kernel_interface.h"
#include "devdrv_mem_alloc.h"
#ifdef CFG_FEATURE_SYSFS_DUMP_DFX
#include "devdrv_pcie_dump_dfx.h"
#endif
#ifdef DRV_UT
#define STATIC
#else
#define STATIC static
#endif
STATIC int g_sysfs_davinci_dev_id = 0;
STATIC struct devdrv_pci_ctrl *devdrv_sysfs_get_pci_ctrl_by_dev(ka_device_t *dev)
{
struct devdrv_pci_ctrl *pci_ctrl = NULL;
ka_pci_dev_t *pdev = ka_pci_to_pci_dev(dev);
struct devdrv_pdev_ctrl *pdev_ctrl = (struct devdrv_pdev_ctrl *)ka_pci_get_drvdata(pdev);
if (pdev_ctrl == NULL) {
devdrv_err("Input parameter is invalid.\n");
return NULL;
}
pci_ctrl = pdev_ctrl->pci_ctrl[g_sysfs_davinci_dev_id];
return pci_ctrl;
}
STATIC u32 devdrv_sysfs_get_devid_by_dev(ka_device_t *dev)
{
struct devdrv_pci_ctrl *pci_ctrl = devdrv_sysfs_get_pci_ctrl_by_dev(dev);
if (pci_ctrl == NULL) {
devdrv_err("Input parameter is invalid.\n");
return MAX_DEV_CNT;
}
return pci_ctrl->dev_id;
}
STATIC int devdrv_sysfs_common_msg_send(u32 devid, void *data, u32 *real_out_len)
{
return devdrv_common_msg_send(devid, data, DEVDRV_SYSFS_MSG_IN_BYTES, (u32)sizeof(struct devdrv_sysfs_msg),
real_out_len, DEVDRV_COMMON_MSG_SYSFS);
}
STATIC ssize_t devdrv_sysfs_link_info_show(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
struct devdrv_pci_ctrl *pci_ctrl = devdrv_sysfs_get_pci_ctrl_by_dev(dev);
struct devdrv_sysfs_msg *msg = NULL;
u32 real_out_len = 0;
int ret;
if ((pci_ctrl == NULL) || (pci_ctrl->pdev == NULL)) {
devdrv_err("Pci_ctrl or pdev is null \n");
return 0;
}
msg = devdrv_kzalloc(sizeof(struct devdrv_sysfs_msg), KA_GFP_KERNEL | __KA_GFP_ACCOUNT);
if (msg == NULL) {
devdrv_err("sysfs_msg malloc failed.\n");
return 0;
}
msg->type = DEVDRV_SYSFS_LINK_INFO;
devdrv_info("devdrv sysfs show link info.(dev_id=%u)\n", pci_ctrl->dev_id);
if (pci_ctrl->ops.get_peh_link_info != NULL) {
ret = pci_ctrl->ops.get_peh_link_info(pci_ctrl->pdev, &(msg->link_info.link_speed),
&(msg->link_info.link_width), &(msg->link_info.link_status));
} else {
ret = devdrv_sysfs_common_msg_send(pci_ctrl->dev_id, (void *)msg, &real_out_len);
}
if (ret != 0) {
devdrv_err("Common msg send failed.\n");
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "read link_info fail, ret:%d\n", ret);
devdrv_kfree(msg);
return ret == -1 ? 0 : ret;
}
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "link speed: %u, link width: %u, link_status: 0x%x\n",
msg->link_info.link_speed, msg->link_info.link_width, msg->link_info.link_status);
devdrv_kfree(msg);
return ret == -1 ? 0 : ret;
}
STATIC ssize_t devdrv_sysfs_rx_para_show(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
u32 devid;
u32 real_out_len = 0;
u32 offset = 0;
u32 i;
int ret;
struct devdrv_sysfs_msg *msg = devdrv_kzalloc(sizeof(struct devdrv_sysfs_msg), KA_GFP_KERNEL | __KA_GFP_ACCOUNT);
if (msg == NULL) {
devdrv_err("sysfs_msg malloc failed.\n");
return 0;
}
msg->type = DEVDRV_SYSFS_RX_PARA;
devdrv_info("devdrv sysfs show rx para.\n");
devid = devdrv_sysfs_get_devid_by_dev(dev);
if (devid >= MAX_DEV_CNT) {
devdrv_err("Get dev_id failed. (dev_id=%u)\n", devid);
devdrv_kfree(msg);
return 0;
}
devdrv_info("Get dev_id success. (dev_id=%u)\n", devid);
ret = devdrv_sysfs_common_msg_send(devid, (void *)msg, &real_out_len);
if (ret != 0) {
devdrv_err("Common msg send failed. (dev_id=%u)\n", devid);
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "read rx_para fail, ret:%d\n", ret);
if (ret != -1) {
offset = (u32)ret;
}
devdrv_kfree(msg);
return offset;
}
for (i = 0; i < DEVDRV_SYSFS_RX_LANE_MAX; i++) {
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
"lane%u att:%-10u gain:%-10u boost:%-10u tap1:%-10u tap2:%-10u\n", i,
msg->rx_para.lane_rx_para[i].att, msg->rx_para.lane_rx_para[i].gain,
msg->rx_para.lane_rx_para[i].boost, msg->rx_para.lane_rx_para[i].tap1,
msg->rx_para.lane_rx_para[i].tap2);
if (ret != -1) {
offset += (u32)ret;
} else {
devdrv_err("snprintf_s failed.\n");
devdrv_kfree(msg);
return 0;
}
}
devdrv_kfree(msg);
return offset;
}
STATIC ssize_t devdrv_sysfs_tx_para_show(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
u32 devid;
u32 real_out_len = 0;
u32 offset = 0;
u32 i;
int ret;
struct devdrv_sysfs_msg *msg = devdrv_kzalloc(sizeof(struct devdrv_sysfs_msg), KA_GFP_KERNEL | __KA_GFP_ACCOUNT);
if (msg == NULL) {
devdrv_err("sysfs_msg malloc failed.\n");
return 0;
}
msg->type = DEVDRV_SYSFS_TX_PARA;
devdrv_info("devdrv sysfs show tx para.\n");
devid = devdrv_sysfs_get_devid_by_dev(dev);
if (devid >= MAX_DEV_CNT) {
devdrv_err("Get dev_id failed. (dev_id=%u)\n", devid);
devdrv_kfree(msg);
return 0;
}
devdrv_info("Get devid success. (dev_id=%u)\n", devid);
ret = devdrv_sysfs_common_msg_send(devid, (void *)msg, &real_out_len);
if (ret != 0) {
devdrv_err("Common msg send failed. (dev_id=%u)\n", devid);
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "read tx_para fail, ret:%d\n", ret);
if (ret != -1) {
offset = (u32)ret;
}
devdrv_kfree(msg);
return offset;
}
for (i = 0; i < DEVDRV_SYSFS_TX_LANE_MAX; i++) {
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
"lane%u pre:%-10u main:%-10u post:%-10u\n", i, msg->tx_para.lane_tx_para[i].pre,
msg->tx_para.lane_tx_para[i].main, msg->tx_para.lane_tx_para[i].post);
if (ret != -1) {
offset += (u32)ret;
} else {
devdrv_err("snprintf_s failed. (dev_id=%u)\n", devid);
devdrv_kfree(msg);
return 0;
}
}
devdrv_kfree(msg);
return offset;
}
STATIC ssize_t devdrv_sysfs_aer_cnt_show(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
u32 devid;
u32 real_out_len = 0;
int ret;
struct devdrv_sysfs_msg *msg = devdrv_kzalloc(sizeof(struct devdrv_sysfs_msg), KA_GFP_KERNEL | __KA_GFP_ACCOUNT);
if (msg == NULL) {
devdrv_err("sysfs_msg malloc failed.\n");
return 0;
}
msg->type = DEVDRV_SYSFS_AER_COUNT;
devdrv_info("devdrv sysfs show aer count.\n");
devid = devdrv_sysfs_get_devid_by_dev(dev);
if (devid >= MAX_DEV_CNT) {
devdrv_err("Get dev_id failed. (dev_id=%u)", devid);
devdrv_kfree(msg);
return 0;
}
devdrv_info("Get dev_id success. (dev_id=%u)", devid);
ret = devdrv_sysfs_common_msg_send(devid, (void *)msg, &real_out_len);
if (ret != 0) {
devdrv_err("Common msg send failed.\n");
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "read aer count fail, ret:%d\n", ret);
devdrv_kfree(msg);
return ret == -1 ? 0 : ret;
}
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "AER count: %u\n", msg->data[0]);
devdrv_kfree(msg);
return ret == -1 ? 0 : ret;
}
STATIC ssize_t devdrv_sysfs_aer_cnt_store(ka_device_t *dev, ka_device_attribute_t *attr, const char *buf,
size_t count)
{
u32 devid;
u32 real_out_len = 0;
int ret;
struct devdrv_sysfs_msg *msg = devdrv_kzalloc(sizeof(struct devdrv_sysfs_msg), KA_GFP_KERNEL | __KA_GFP_ACCOUNT);
if (msg == NULL) {
devdrv_err("Clear aer count failed, sysfs_msg malloc failed. (uid=%u)\n", ka_task_get_current_cred_uid());
return -EINVAL;
}
msg->type = DEVDRV_SYSFS_AER_CLEAR;
devid = devdrv_sysfs_get_devid_by_dev(dev);
if (devid >= MAX_DEV_CNT) {
devdrv_err("Clear aer count failed, get dev_id failed. (dev_id=%u; uid=%u)\n",
devid, ka_task_get_current_cred_uid());
devdrv_kfree(msg);
return -EINVAL;
}
if (ka_base_strcmp(buf, "clear") == 0) {
ret = devdrv_sysfs_common_msg_send(devid, (void *)msg, &real_out_len);
if (ret != 0) {
devdrv_err("Clear aer count failed, Common msg send failed. (dev_id=%u; uid=%u)\n",
devid, ka_task_get_current_cred_uid());
devdrv_kfree(msg);
return -EINVAL;
}
}
devdrv_info("Clear aer count success. (dev_id=%u; uid=%u)\n", devid, ka_task_get_current_cred_uid());
devdrv_kfree(msg);
return (ssize_t)count;
}
STATIC ssize_t devdrv_sysfs_bdf_to_devid_show(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
struct devdrv_ctrl *ctrl = NULL;
ka_pci_dev_t *pdev = NULL;
ssize_t offset = 0;
u8 bus_num = 0;
u8 device_num = 0;
u8 func_num = 0;
int ret;
u32 i, udevid, add_id;
devdrv_info("devdrv sysfs show bdf and dev_id.\n");
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
"bdf udevid add_id\n");
if (ret != -1) {
offset += ret;
}
for (i = 0; i < MAX_DEV_CNT; i++) {
ctrl = devdrv_get_devctrl_by_id(i);
if (ctrl == NULL) {
continue;
}
if ((ctrl->dev_id < MAX_DEV_CNT) && (ctrl->pdev != NULL) &&
(ctrl->startup_flg != DEVDRV_DEV_STARTUP_UNPROBED)) {
pdev = ctrl->pdev;
bus_num = ka_pci_get_bus_number(pdev);
device_num = KA_PCI_SLOT(ka_pci_get_devfn(pdev));
func_num = KA_PCI_FUNC(ka_pci_get_devfn(pdev));
add_id = ctrl->dev_id;
(void)uda_add_id_to_udevid(add_id, &udevid);
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
"%02x:%02x.%hhu %-6u %-5u\n", bus_num, device_num, func_num, udevid, add_id);
if (ret != -1) {
offset += ret;
}
}
}
return offset;
}
STATIC ssize_t devdrv_sysfs_get_dev_id(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
u32 dev_id;
int ret;
ssize_t offset = 0;
(void)attr;
dev_id = devdrv_sysfs_get_devid_by_dev(dev);
if (dev_id >= MAX_DEV_CNT) {
devdrv_err("Invalid dev_id. (dev_id=%u)\n", dev_id);
return offset;
}
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "%u\n", dev_id);
if (ret >= 0) {
offset += ret;
}
return offset;
}
STATIC ssize_t devdrv_sysfs_get_davinci_dev_id(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
int ret;
ssize_t offset = 0;
(void)attr;
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "%d\n", g_sysfs_davinci_dev_id);
if (ret >= 0) {
offset += ret;
}
return offset;
}
STATIC ssize_t devdrv_sysfs_set_davinci_dev_id(ka_device_t *dev,
ka_device_attribute_t *attr,
const char *buf,
size_t count)
{
u32 val = 0;
int davinci_dev_num = devdrv_get_davinci_dev_num_by_pdev(ka_pci_to_pci_dev(dev));
if (davinci_dev_num < 0) {
devdrv_err("davinci_dev_num is invalid.\n");
return (ssize_t)count;
}
if (ka_base_kstrtou32(buf, 0, &val) < 0) {
devdrv_err("Call ka_base_kstrtou32 failed.\n");
return (ssize_t)count;
}
if (val >= (u32)davinci_dev_num) {
devdrv_err("Input parameter is invalid. (val=%u; devid max in pdev=%d)\n", val, davinci_dev_num);
return (ssize_t)count;
}
g_sysfs_davinci_dev_id = (int)val;
return (ssize_t)count;
}
STATIC ssize_t devdrv_sysfs_get_davinci_dev_num(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
int ret;
ssize_t offset = 0;
(void)attr;
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "%d\n", devdrv_get_davinci_dev_num_by_pdev(ka_pci_to_pci_dev(dev)));
if (ret >= 0) {
offset += ret;
}
return offset;
}
STATIC ssize_t devdrv_sysfs_get_chip_id(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
struct devdrv_pci_ctrl *pci_ctrl = devdrv_sysfs_get_pci_ctrl_by_dev(dev);
u32 chip_id;
int ret;
ssize_t offset = 0;
(void)attr;
if (pci_ctrl == NULL) {
devdrv_err("Get pci_ctrl failed.\n");
return 0;
}
chip_id = (u32)pci_ctrl->shr_para->chip_id;
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "%u\n", chip_id);
if (ret >= 0) {
offset += ret;
}
return offset;
}
STATIC ssize_t devdrv_sysfs_get_bus_name(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
struct devdrv_ctrl *ctrl = NULL;
ka_pci_bus_t *bus = NULL;
ka_pci_dev_t *pdev = NULL;
u32 dev_id;
int ret;
ssize_t offset = 0;
(void)attr;
dev_id = devdrv_sysfs_get_devid_by_dev(dev);
if (dev_id >= MAX_DEV_CNT) {
devdrv_err("Invalid dev_id. (dev_id=%u)\n", dev_id);
return offset;
}
ctrl = devdrv_get_bottom_half_devctrl_by_id(dev_id);
if (ctrl == NULL) {
devdrv_err("Get dev_ctrl failed. (dev_id=%u)\n", dev_id);
return offset;
}
bus = ctrl->bus;
if (bus != NULL) {
pdev = bus->self;
if (pdev == NULL) {
devdrv_err("Get bus fail, bus->self is NULL. (dev_id=%u)\n", dev_id);
return offset;
}
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "%04x:%02x:%02x.%u\n", ka_pci_domain_nr(bus),
ka_pci_get_bus_number(pdev), KA_PCI_SLOT(ka_pci_get_devfn(pdev)), KA_PCI_FUNC(ka_pci_get_devfn(pdev)));
if (ret >= 0) {
offset += ret;
}
}
return offset;
}
STATIC ssize_t devdrv_sysfs_set_hotreset_flag(ka_device_t *dev,
ka_device_attribute_t *attr,
const char *buf,
size_t count)
{
struct devdrv_pci_ctrl *pci_ctrl = devdrv_sysfs_get_pci_ctrl_by_dev(dev);
unsigned long val = 0;
ssize_t result;
u32 devid;
(void)attr;
if (pci_ctrl == NULL) {
devdrv_err("Set hotreset flag failed, get pci_ctrl failed. (uid=%u)\n", ka_task_get_current_cred_uid());
return -EINVAL;
}
devid = pci_ctrl->dev_id;
result = ka_base_kstrtoul(buf, 0, &val);
if (result < 0) {
devdrv_err("Set hotreset flag failed, ka_base_kstrtoul failed. (dev_id=%u; uid=%u; result=%ld)\n",
devid, ka_task_get_current_cred_uid(), result);
return result;
}
if (val == 1) {
if (pci_ctrl != NULL) {
if (pci_ctrl->shr_para != NULL) {
pci_ctrl->shr_para->hot_reset_pcie_flag = DEVDRV_PCIE_HOT_RESET_FLAG;
devdrv_info("Set hotreset flag success. (dev_id=%u; uid=%u; val=%lu)\n",
devid, ka_task_get_current_cred_uid(), val);
return (ssize_t)count;
}
}
}
devdrv_info("No need to set hotreset flag. (dev_id=%u; uid=%u; val=%lu)\n", devid, ka_task_get_current_cred_uid(), val);
return (ssize_t)count;
}
STATIC ssize_t devdrv_sysfs_get_common_msg(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
struct devdrv_pci_ctrl *pci_ctrl = devdrv_sysfs_get_pci_ctrl_by_dev(dev);
u32 dev_id;
int ret;
ssize_t offset = 0;
struct devdrv_sysfs_msg *msg = NULL;
u32 real_out_len = 0;
int i;
u64 tx_total_cnt;
u64 tx_success_cnt;
u64 tx_failed_cnt1;
u64 tx_failed_cnt2;
u64 tx_failed_cnt3;
u64 tx_failed_cnt4;
u64 tx_failed_cnt5;
u64 rx_total_cnt;
u64 rx_success_cnt;
u64 rx_work_max_time;
u64 rx_work_delay_cnt;
char *common_str[DEVDRV_COMMON_MSG_TYPE_MAX] = {DEVDRV_PCIVNIC, DEVDRV_SMMU, DEVDRV_DEVMM, DEVDRV_VMNG,
DEVDRV_PROFILE, DEVDRV_DEVMAN, DEVDRV_TSDRV, DEVDRV_HDC,
DEVDRV_SYSFS, DEVDRV_ESCHED, DEVDRV_PROCMNG, DEVDRV_TEST,
DEVDRV_UDIS};
(void)attr;
if (pci_ctrl == NULL) {
devdrv_err("Get pci_ctrl failed.\n");
return 0;
}
dev_id = pci_ctrl->dev_id;
msg = (struct devdrv_sysfs_msg *)devdrv_kzalloc(sizeof(struct devdrv_sysfs_msg), KA_GFP_KERNEL | __KA_GFP_ACCOUNT);
if (msg == NULL) {
devdrv_err("devdrv_kzalloc failed.\n");
return 0;
}
msg->type = DEVDRV_SYSFS_COMMON_MSG;
ret = devdrv_sysfs_common_msg_send(dev_id, (void *)msg, &real_out_len);
if (ret != 0) {
devdrv_kfree(msg);
msg = NULL;
devdrv_err("Common msg send failed.\n");
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "read common msg fail, ret:%d\n", ret);
return ret == -1 ? 0 : ret;
}
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
"\nhost chan| tx_total | tx_success | inval | nodev |"
" enosys |timedout| default|"
" rx_total_cnt | rx_success_cnt | cost_time|work_delay\n");
if (ret != -1) {
offset += ret;
}
for (i = 0; i < DEVDRV_COMMON_MSG_TYPE_MAX; i++) {
tx_total_cnt = pci_ctrl->msg_dev->common_msg.com_msg_stat[i].tx_total_cnt;
tx_success_cnt = pci_ctrl->msg_dev->common_msg.com_msg_stat[i].tx_success_cnt;
tx_failed_cnt1 = pci_ctrl->msg_dev->common_msg.com_msg_stat[i].tx_einval_err;
tx_failed_cnt2 = pci_ctrl->msg_dev->common_msg.com_msg_stat[i].tx_enodev_err;
tx_failed_cnt3 = pci_ctrl->msg_dev->common_msg.com_msg_stat[i].tx_enosys_err;
tx_failed_cnt4 = pci_ctrl->msg_dev->common_msg.com_msg_stat[i].tx_etimedout_err;
tx_failed_cnt5 = pci_ctrl->msg_dev->common_msg.com_msg_stat[i].tx_default_err;
rx_total_cnt = pci_ctrl->msg_dev->common_msg.com_msg_stat[i].rx_total_cnt;
rx_success_cnt = pci_ctrl->msg_dev->common_msg.com_msg_stat[i].rx_success_cnt;
rx_work_max_time = pci_ctrl->msg_dev->common_msg.com_msg_stat[i].rx_work_max_time;
rx_work_delay_cnt = pci_ctrl->msg_dev->common_msg.com_msg_stat[i].rx_work_delay_cnt;
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1, " %s|%-16llu|%-16llu|%-8llu|"
"%-8llu|%-8llu|%-8llu|%-8llu|%-16llu|%-16llu|%-10llu|%-10llu\n",
common_str[i], tx_total_cnt, tx_success_cnt, tx_failed_cnt1, tx_failed_cnt2,
tx_failed_cnt3, tx_failed_cnt4, tx_failed_cnt5, rx_total_cnt, rx_success_cnt,
rx_work_max_time, rx_work_delay_cnt);
if (ret != -1) {
offset += ret;
}
}
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
"\ndev chan| tx_total | tx_success | inval | nodev |"
" enosys |timedout| default|"
" rx_total_cnt | rx_success_cnt | cost_time|work_delay\n");
if (ret != -1) {
offset += ret;
}
for (i = 0; i < DEVDRV_COMMON_MSG_TYPE_MAX; i++) {
tx_total_cnt = msg->common_stat[i].tx_total_cnt;
tx_success_cnt = msg->common_stat[i].tx_success_cnt;
tx_failed_cnt1 = msg->common_stat[i].tx_einval_err;
tx_failed_cnt2 = msg->common_stat[i].tx_enodev_err;
tx_failed_cnt3 = msg->common_stat[i].tx_enosys_err;
tx_failed_cnt4 = msg->common_stat[i].tx_etimedout_err;
tx_failed_cnt5 = msg->common_stat[i].tx_default_err;
rx_total_cnt = msg->common_stat[i].rx_total_cnt;
rx_success_cnt = msg->common_stat[i].rx_success_cnt;
rx_work_max_time = msg->common_stat[i].rx_work_max_time;
rx_work_delay_cnt = msg->common_stat[i].rx_work_delay_cnt;
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1, " %s|%-16llu|%-16llu|%-8llu|"
"%-8llu|%-8llu|%-8llu|%-8llu|%-16llu|%-16llu|%-10llu|%-10llu\n",
common_str[i], tx_total_cnt, tx_success_cnt, tx_failed_cnt1, tx_failed_cnt2,
tx_failed_cnt3, tx_failed_cnt4, tx_failed_cnt5, rx_total_cnt, rx_success_cnt,
rx_work_max_time, rx_work_delay_cnt);
if (ret != -1) {
offset += ret;
}
}
devdrv_kfree(msg);
msg = NULL;
return offset;
}
STATIC int devdrv_sysfs_fill_buf(struct devdrv_msg_dev *msg_dev, struct devdrv_sysfs_msg *msg, char *buf)
{
int ret;
u32 i;
u64 tx_total_cnt;
u64 tx_success_cnt;
u64 tx_no_callback;
u64 tx_failed_cnt1;
u64 tx_failed_cnt2;
u64 tx_failed_cnt3;
u64 tx_failed_cnt4;
u64 tx_failed_cnt5;
u64 tx_failed_cnt6;
u64 rx_total_cnt;
u64 rx_success_cnt;
u64 rx_para_err;
u64 rx_work_max_time;
u64 rx_work_delay_cnt;
u32 msg_type;
ssize_t offset = 0;
struct devdrv_msg_chan *chan = NULL;
char *non_str[devdrv_msg_client_max] = {DEVDRV_PCIVNIC, DEVDRV_SMMU, DEVDRV_DEVMM, DEVDRV_COMMON,
DEVDRV_DEVMAN, DEVDRV_TSDRV, DEVDRV_HDC, DEVDRV_QUEUE, DEVDRV_S2S};
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
"\nhost type| tx_total | tx_success |no_callback|len_err|stat_abno|irqtimeout|"
"timeout|proc_err|inva_para|"
" rx_total | rx_success |para_err|cost_time|work_delay\n");
if (ret != -1) {
offset += ret;
}
for (i = 0; i < msg_dev->chan_cnt; i++) {
chan = &(msg_dev->msg_chan[i]);
if ((chan->status == AGENTDRV_ENABLE) && (chan->queue_type == NON_TRANSPARENT_MSG_QUEUE)) {
tx_total_cnt = chan->chan_stat.tx_total_cnt;
tx_success_cnt = chan->chan_stat.tx_success_cnt;
tx_no_callback = chan->chan_stat.tx_no_callback;
tx_failed_cnt1 = chan->chan_stat.tx_len_check_err;
tx_failed_cnt2 = chan->chan_stat.tx_status_abnormal_err;
tx_failed_cnt3 = chan->chan_stat.tx_irq_timeout_err;
tx_failed_cnt4 = chan->chan_stat.tx_timeout_err;
tx_failed_cnt5 = chan->chan_stat.tx_process_err;
tx_failed_cnt6 = chan->chan_stat.tx_invalid_para_err;
rx_total_cnt = chan->chan_stat.rx_total_cnt;
rx_success_cnt = chan->chan_stat.rx_success_cnt;
rx_para_err = chan->chan_stat.rx_para_err;
rx_work_max_time = chan->chan_stat.rx_work_max_time;
rx_work_delay_cnt = chan->chan_stat.rx_work_delay_cnt;
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
" %s|%-14llu|%-14llu|%-11llu|%-7llu|%-9llu|%-10llu|%-7llu|%-8llu|%-9llu|%-14llu|"
"%-14llu|%-8llu|%-9llu|%-10llu\n",
non_str[chan->msg_type], tx_total_cnt, tx_success_cnt, tx_no_callback, tx_failed_cnt1,
tx_failed_cnt2, tx_failed_cnt3, tx_failed_cnt4, tx_failed_cnt5, tx_failed_cnt6,
rx_total_cnt, rx_success_cnt, rx_para_err, rx_work_max_time, rx_work_delay_cnt);
if (ret != -1) {
offset += ret;
}
}
}
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
"\ndev type| tx_total | tx_success |no_callback|len_err| dma_copy| |"
"timeout|proc_err|inva_para|"
" rx_total | rx_success |para_err|cost_time|work_delay\n");
if (ret != -1) {
offset += ret;
}
for (i = 0; i < devdrv_msg_client_max; i++) {
if ((msg->non_trans_stat[i].msg_type == 0) || (msg->non_trans_stat[i].msg_type >= devdrv_msg_client_max)) {
continue;
}
msg_type = (u32)msg->non_trans_stat[i].msg_type;
tx_total_cnt = msg->non_trans_stat[i].tx_total_cnt;
tx_success_cnt = msg->non_trans_stat[i].tx_success_cnt;
tx_no_callback = msg->non_trans_stat[i].tx_no_callback;
tx_failed_cnt1 = msg->non_trans_stat[i].tx_len_check_err;
tx_failed_cnt2 = msg->non_trans_stat[i].tx_dma_copy_err;
tx_failed_cnt3 = msg->non_trans_stat[i].tx_timeout_err;
tx_failed_cnt4 = msg->non_trans_stat[i].tx_process_err;
tx_failed_cnt5 = msg->non_trans_stat[i].tx_invalid_para_err;
rx_total_cnt = msg->non_trans_stat[i].rx_total_cnt;
rx_success_cnt = msg->non_trans_stat[i].rx_success_cnt;
rx_para_err = msg->non_trans_stat[i].rx_para_err;
rx_work_max_time = msg->non_trans_stat[i].rx_work_max_time;
rx_work_delay_cnt = msg->non_trans_stat[i].rx_work_delay_cnt;
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
" %s|%-14llu|%-14llu|%-11llu|%-7llu|%-9llu|%-10llu|%-7llu|%-8llu|%-9llu|%-14llu|"
"%-14llu|%-8llu|%-9llu|%-10llu\n", non_str[msg_type], tx_total_cnt, tx_success_cnt,
tx_no_callback, tx_failed_cnt1, tx_failed_cnt2, 0, tx_failed_cnt3, tx_failed_cnt4,
tx_failed_cnt5, rx_total_cnt, rx_success_cnt, rx_para_err, rx_work_max_time,
rx_work_delay_cnt);
if (ret != -1) {
offset += ret;
}
}
return (int)offset;
}
STATIC ssize_t devdrv_sysfs_get_non_trans_msg(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
struct devdrv_pci_ctrl *pci_ctrl = devdrv_sysfs_get_pci_ctrl_by_dev(dev);
u32 dev_id;
int ret;
ssize_t offset = 0;
struct devdrv_sysfs_msg *msg = NULL;
struct devdrv_msg_dev *msg_dev = NULL;
u32 real_out_len = 0;
(void)attr;
if (pci_ctrl == NULL) {
devdrv_err("Get pci_ctrl failed.\n");
return 0;
}
dev_id = pci_ctrl->dev_id;
msg_dev = pci_ctrl->msg_dev;
msg = (struct devdrv_sysfs_msg *)devdrv_kzalloc(sizeof(struct devdrv_sysfs_msg), KA_GFP_KERNEL | __KA_GFP_ACCOUNT);
if (msg == NULL) {
devdrv_err("malloc failed.\n");
return 0;
}
msg->type = DEVDRV_SYSFS_NON_TRANS_MSG;
ret = devdrv_sysfs_common_msg_send(dev_id, (void *)msg, &real_out_len);
if (ret != 0) {
devdrv_kfree(msg);
msg = NULL;
devdrv_err("Common msg send failed.\n");
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1, "read non trans fail, ret:%d\n", ret);
return ret == -1 ? 0 : ret;
}
offset = devdrv_sysfs_fill_buf(msg_dev, msg, buf);
devdrv_kfree(msg);
msg = NULL;
return offset;
}
STATIC ssize_t devdrv_sysfs_sync_dma_info_show(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
struct devdrv_pci_ctrl *pci_ctrl = devdrv_sysfs_get_pci_ctrl_by_dev(dev);
struct devdrv_sysfs_msg *msg = NULL;
struct devdrv_msg_dev *msg_dev = NULL;
struct devdrv_dma_dev *dma_dev = NULL;
u32 dev_id;
u32 real_out_len = 0;
int ret;
ssize_t offset = 0;
u32 i;
if (pci_ctrl == NULL) {
devdrv_err("Get pci_ctrl failed.\n");
return 0;
}
dev_id = pci_ctrl->dev_id;
msg_dev = pci_ctrl->msg_dev;
dma_dev = pci_ctrl->dma_dev;
msg = (struct devdrv_sysfs_msg *)devdrv_kzalloc(sizeof(struct devdrv_sysfs_msg), KA_GFP_KERNEL | __KA_GFP_ACCOUNT);
if (msg == NULL) {
devdrv_err("malloc failed.\n");
return 0;
}
msg->type = DEVDRV_SYSFS_SYNC_DMA_INFO;
ret = devdrv_sysfs_common_msg_send(dev_id, (void *)msg, &real_out_len);
if (ret != 0) {
devdrv_err("Common msg send failed.\n");
ret = snprintf_s(buf, KA_MM_PAGE_SIZE, KA_MM_PAGE_SIZE - 1,
"read dma info fail, ret:%d\n", ret);
devdrv_kfree(msg);
msg = NULL;
return (ret == -1) ? 0 : ret;
}
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
"\ndev |syn_submit|asy_submit|sml_submit|tot_sync|trg_remot|trg_128|done_int|"
"re_sched|done_work|syn_proc|max_cb|new_cb|cb_10s|cb_10ms|asy_proc|err_int|err_work|"
"max_task|sq_idle\n");
if (ret != -1) {
offset += ret;
}
for (i = 0; i < DEVDRV_SYSFS_DMA_CHAN_NUM; i++) {
if (msg->sync_dma_stat[i].flag == DEVDRV_DISABLE) {
continue;
}
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
" %-4u|%-10llu|%-10llu|%-10llu|%-8llu|%-9llu|%-7llu|%-8llu|%-8llu|%-9llu|"
"%-8llu|%-6llu|%-6llu|%-6llu|%-7llu|%-8llu|%-7llu|%-8llu|%-8llu|%-7llu\n",
i,
msg->sync_dma_stat[i].sync_submit_cnt,
msg->sync_dma_stat[i].async_submit_cnt,
msg->sync_dma_stat[i].sml_submit_cnt,
msg->sync_dma_stat[i].sync_submit_cnt + msg->sync_dma_stat[i].sml_submit_cnt,
msg->sync_dma_stat[i].trigger_remot_int_cnt,
msg->sync_dma_stat[i].trigger_local_128,
msg->sync_dma_stat[i].done_int_cnt,
msg->sync_dma_stat[i].re_schedule_cnt,
msg->sync_dma_stat[i].done_tasklet_in_cnt,
msg->sync_dma_stat[i].sync_sem_up_cnt,
msg->sync_dma_stat[i].max_callback_time,
msg->sync_dma_stat[i].new_callback_time,
msg->sync_dma_stat[i].callback_time_over10s,
msg->sync_dma_stat[i].callback_time_over10ms,
msg->sync_dma_stat[i].async_proc_cnt,
msg->sync_dma_stat[i].err_int_cnt,
msg->sync_dma_stat[i].err_work_cnt,
msg->sync_dma_stat[i].max_task_op_time,
msg->sync_dma_stat[i].sq_idle_bd_cnt);
if (ret != -1) {
offset += ret;
}
}
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1, "\nhost\n");
if (ret != -1) {
offset += ret;
}
for (i = 0; i < dma_dev->remote_chan_num; i++) {
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1,
" %-4d|%-10llu|%-10llu|%-10llu|%-8llu|%-9llu|%-7llu|%-8llu|%-8llu|%-9llu|"
"%-8llu|%-6llu|%-6llu|%-6llu|%-7llu|%-8llu|%-7llu|%-8llu|%-8llu|%-7llu\n",
i,
dma_dev->dma_chan[i].status.sync_submit_cnt,
dma_dev->dma_chan[i].status.async_submit_cnt,
dma_dev->dma_chan[i].status.sml_submit_cnt,
dma_dev->dma_chan[i].status.sync_submit_cnt +
dma_dev->dma_chan[i].status.sml_submit_cnt,
dma_dev->dma_chan[i].status.trigger_remot_int_cnt,
dma_dev->dma_chan[i].status.trigger_local_128,
dma_dev->dma_chan[i].status.done_int_cnt,
dma_dev->dma_chan[i].status.re_schedule_cnt,
dma_dev->dma_chan[i].status.done_tasklet_in_cnt,
dma_dev->dma_chan[i].status.sync_sem_up_cnt,
dma_dev->dma_chan[i].status.max_callback_time,
dma_dev->dma_chan[i].status.new_callback_time,
dma_dev->dma_chan[i].status.callback_time_over10s,
dma_dev->dma_chan[i].status.callback_time_over10ms,
dma_dev->dma_chan[i].status.async_proc_cnt,
dma_dev->dma_chan[i].status.err_int_cnt,
dma_dev->dma_chan[i].status.err_work_cnt,
dma_dev->dma_chan[i].status.max_task_op_time,
dma_dev->dma_chan[i].status.sq_idle_bd_cnt);
if (ret != -1) {
offset += ret;
}
}
devdrv_kfree(msg);
msg = NULL;
return offset;
}
#define PCIE_AER_ROOT_ERR 1U
#define PCIE_AER_CFG_SPACE_UNCORRECT_ERR 2U
#define PCIE_AER_CFG_SPACE_CORRECT_ERR 3U
STATIC struct pcie_aer_info_item g_pcie_aer_info_table[] = {
PCIE_AER_NODE(PCIE_AER_ROOT_ERR, 0U, "correct err msg recv"),
PCIE_AER_NODE(PCIE_AER_ROOT_ERR, 1U, "multi correct err msg recv"),
PCIE_AER_NODE(PCIE_AER_ROOT_ERR, 2U, "incorrect err msg recv"),
PCIE_AER_NODE(PCIE_AER_ROOT_ERR, 3U, "multi incorrect err msg recv"),
PCIE_AER_NODE(PCIE_AER_ROOT_ERR, 4U, "first incorrect err"),
PCIE_AER_NODE(PCIE_AER_ROOT_ERR, 5U, "noncritical msg recv"),
PCIE_AER_NODE(PCIE_AER_ROOT_ERR, 6U, "critical err msg recv"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 4U, "data link protocol err status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 5U, "surprise down status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 12U, "poisoned TLP status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 13U, "credit protocol err status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 14U, "completion timeout status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 15U, "completion abort status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 16U, "unexpected completion status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 17U, "receive overflow status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 18U, "malformed TLP err status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 19U, "ECRC err status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 20U, "unsupported req err status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 21U, "ACS violation status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 22U, "incorrect internal err status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 23U, "multicast block status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 24U, "atomicop egress block status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 25U, "TLP prefix block err status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_UNCORRECT_ERR, 26U, "poisoned TLP block status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_CORRECT_ERR, 0U, "rx err status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_CORRECT_ERR, 6U, "bad tlp status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_CORRECT_ERR, 7U, "bad dllp status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_CORRECT_ERR, 8U, "reply num rollover status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_CORRECT_ERR, 12U, "reply timer timeout status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_CORRECT_ERR, 13U, "advisory noncritical err status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_CORRECT_ERR, 14U, "correct internal err status"),
PCIE_AER_NODE(PCIE_AER_CFG_SPACE_CORRECT_ERR, 15U, "header log overflow status"),
};
STATIC ssize_t devdrv_sysfs_aer_info_show(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
u32 num;
u32 i;
ssize_t offset = 0;
int ret;
num = sizeof(g_pcie_aer_info_table) / sizeof(struct pcie_aer_info_item);
for (i = 0; i < num; i++) {
if (g_pcie_aer_info_table[i].count != 0) {
ret = snprintf_s(buf + offset, KA_MM_PAGE_SIZE - offset, KA_MM_PAGE_SIZE - offset - 1, "%-31s:%u\n",
g_pcie_aer_info_table[i].describe, g_pcie_aer_info_table[i].count);
if (ret != -1) {
offset += ret;
}
}
}
return offset;
}
void devdrv_sysfs_update_aer_count(unsigned char aer_regs, unsigned char aer_bits)
{
u32 num;
u32 i;
bool update_finish = false;
num = sizeof(g_pcie_aer_info_table) / sizeof(struct pcie_aer_info_item);
for (i = 0; i < num; i++) {
if ((g_pcie_aer_info_table[i].regs == aer_regs) && (g_pcie_aer_info_table[i].bits == aer_bits)) {
g_pcie_aer_info_table[i].count++;
update_finish = true;
break;
}
}
if (!update_finish) {
devdrv_err("update aer info failed. (aer_regs=%u, aer_bits=%u).\n", (u32)aer_regs, (u32)aer_bits);
}
return;
}
KA_EXPORT_SYMBOL(devdrv_sysfs_update_aer_count);
STATIC ssize_t devdrv_sysfs_dump_dfx_part1_show(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
#ifndef CFG_FEATURE_SYSFS_DUMP_DFX
return -1;
#else
return soc_misc_pcie_sysfs_dump_dfx_info(buf, 0);
#endif
}
STATIC ssize_t devdrv_sysfs_dump_dfx_part2_show(ka_device_t *dev, ka_device_attribute_t *attr, char *buf)
{
#ifndef CFG_FEATURE_SYSFS_DUMP_DFX
return -1;
#else
return soc_misc_pcie_sysfs_dump_dfx_info(buf, 1);
#endif
}
static KA_DRIVER_DEVICE_ATTR(devdrv_sysfs_link_info, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_link_info_show, NULL);
static KA_DRIVER_DEVICE_ATTR(devdrv_sysfs_rx_para_info, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_rx_para_show, NULL);
static KA_DRIVER_DEVICE_ATTR(devdrv_sysfs_tx_para_info, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_tx_para_show, NULL);
static KA_DRIVER_DEVICE_ATTR(devdrv_sysfs_aer_cnt_info, KA_S_IRUSR | KA_S_IRGRP | KA_S_IWUSR | KA_S_IWGRP, devdrv_sysfs_aer_cnt_show,
devdrv_sysfs_aer_cnt_store);
static KA_DRIVER_DEVICE_ATTR(devdrv_sysfs_bdf_to_devid, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_bdf_to_devid_show, NULL);
static KA_DRIVER_DEVICE_ATTR(davinci_dev_id, KA_S_IRUSR | KA_S_IRGRP | KA_S_IWUSR | KA_S_IWGRP, devdrv_sysfs_get_davinci_dev_id,
devdrv_sysfs_set_davinci_dev_id);
static KA_DRIVER_DEVICE_ATTR(davinci_dev_num, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_get_davinci_dev_num, NULL);
static KA_DRIVER_DEVICE_ATTR(dev_id, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_get_dev_id, NULL);
static KA_DRIVER_DEVICE_ATTR(chip_id, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_get_chip_id, NULL);
static KA_DRIVER_DEVICE_ATTR(bus_name, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_get_bus_name, NULL);
static KA_DRIVER_DEVICE_ATTR(hotreset_flag, KA_S_IWUSR | KA_S_IWGRP, NULL, devdrv_sysfs_set_hotreset_flag);
static KA_DRIVER_DEVICE_ATTR(common_msg, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_get_common_msg, NULL);
static KA_DRIVER_DEVICE_ATTR(non_trans_msg, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_get_non_trans_msg, NULL);
static KA_DRIVER_DEVICE_ATTR(dma_info, KA_S_IRUGO, devdrv_sysfs_sync_dma_info_show, NULL);
static KA_DRIVER_DEVICE_ATTR(aer_info, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_aer_info_show, NULL);
static KA_DRIVER_DEVICE_ATTR(dump_dfx_part1, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_dump_dfx_part1_show, NULL);
static KA_DRIVER_DEVICE_ATTR(dump_dfx_part2, KA_S_IRUSR | KA_S_IRGRP, devdrv_sysfs_dump_dfx_part2_show, NULL);
static ka_attribute_t *g_devdrv_sysfs_attrs[] = {
ka_fs_get_dev_attr(dev_attr_devdrv_sysfs_link_info)
ka_fs_get_dev_attr(dev_attr_devdrv_sysfs_rx_para_info)
ka_fs_get_dev_attr(dev_attr_devdrv_sysfs_tx_para_info)
ka_fs_get_dev_attr(dev_attr_devdrv_sysfs_aer_cnt_info)
ka_fs_get_dev_attr(dev_attr_devdrv_sysfs_bdf_to_devid)
ka_fs_get_dev_attr(dev_attr_davinci_dev_id)
ka_fs_get_dev_attr(dev_attr_davinci_dev_num)
ka_fs_get_dev_attr(dev_attr_dev_id)
ka_fs_get_dev_attr(dev_attr_chip_id)
ka_fs_get_dev_attr(dev_attr_bus_name)
ka_fs_get_dev_attr(dev_attr_hotreset_flag)
ka_fs_get_dev_attr(dev_attr_aer_info)
ka_fs_get_dev_attr(dev_attr_dump_dfx_part1)
ka_fs_get_dev_attr(dev_attr_dump_dfx_part2)
NULL,
};
static const ka_attribute_group_t g_devdrv_sysfs_group = {
ka_fs_init_ag_attrs(g_devdrv_sysfs_attrs)
};
static ka_attribute_t *g_devdrv_sysfs_msg_attrs[] = {
ka_fs_get_dev_attr(dev_attr_common_msg)
ka_fs_get_dev_attr(dev_attr_non_trans_msg)
ka_fs_get_dev_attr(dev_attr_dma_info)
NULL,
};
static const ka_attribute_group_t g_devdrv_sysfs_msg_group = {
ka_fs_init_ag_attrs(g_devdrv_sysfs_msg_attrs)
ka_fs_init_ag_name("msg")
};
int devdrv_sysfs_init(ka_pci_dev_t *pdev)
{
int ret;
ret = ka_sysfs_create_group(ka_pci_get_dev_kobj(pdev), &g_devdrv_sysfs_group);
if (ret != 0) {
devdrv_err("Call ka_sysfs_create_group failed. (ret=%d)\n", ret);
return -1;
}
ret = ka_sysfs_create_group(ka_pci_get_dev_kobj(pdev), &g_devdrv_sysfs_msg_group);
if (ret != 0) {
devdrv_err("Call ka_sysfs_create_group failed. (ret=%d)\n", ret);
return -1;
}
return 0;
}
void devdrv_sysfs_exit(ka_pci_dev_t *pdev)
{
ka_sysfs_remove_group(ka_pci_get_dev_kobj(pdev), &g_devdrv_sysfs_group);
ka_sysfs_remove_group(ka_pci_get_dev_kobj(pdev), &g_devdrv_sysfs_msg_group);
}