162306a36Sopenharmony_ci// SPDX-License-Identifier: GPL-2.0 262306a36Sopenharmony_ci 362306a36Sopenharmony_ci/* 462306a36Sopenharmony_ci * Copyright 2016-2022 HabanaLabs, Ltd. 562306a36Sopenharmony_ci * All Rights Reserved. 662306a36Sopenharmony_ci */ 762306a36Sopenharmony_ci 862306a36Sopenharmony_ci#include "habanalabs.h" 962306a36Sopenharmony_ci 1062306a36Sopenharmony_ci#include <linux/pci.h> 1162306a36Sopenharmony_ci 1262306a36Sopenharmony_cistatic ssize_t clk_max_freq_mhz_show(struct device *dev, struct device_attribute *attr, char *buf) 1362306a36Sopenharmony_ci{ 1462306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 1562306a36Sopenharmony_ci long value; 1662306a36Sopenharmony_ci 1762306a36Sopenharmony_ci if (!hl_device_operational(hdev, NULL)) 1862306a36Sopenharmony_ci return -ENODEV; 1962306a36Sopenharmony_ci 2062306a36Sopenharmony_ci value = hl_fw_get_frequency(hdev, hdev->asic_prop.clk_pll_index, false); 2162306a36Sopenharmony_ci if (value < 0) 2262306a36Sopenharmony_ci return value; 2362306a36Sopenharmony_ci 2462306a36Sopenharmony_ci hdev->asic_prop.max_freq_value = value; 2562306a36Sopenharmony_ci 2662306a36Sopenharmony_ci return sprintf(buf, "%lu\n", (value / 1000 / 1000)); 2762306a36Sopenharmony_ci} 2862306a36Sopenharmony_ci 2962306a36Sopenharmony_cistatic ssize_t clk_max_freq_mhz_store(struct device *dev, struct device_attribute *attr, 3062306a36Sopenharmony_ci const char *buf, size_t count) 3162306a36Sopenharmony_ci{ 3262306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 3362306a36Sopenharmony_ci int rc; 3462306a36Sopenharmony_ci u64 value; 3562306a36Sopenharmony_ci 3662306a36Sopenharmony_ci if (!hl_device_operational(hdev, NULL)) { 3762306a36Sopenharmony_ci count = -ENODEV; 3862306a36Sopenharmony_ci goto fail; 3962306a36Sopenharmony_ci } 4062306a36Sopenharmony_ci 4162306a36Sopenharmony_ci rc = kstrtoull(buf, 0, &value); 4262306a36Sopenharmony_ci if (rc) { 4362306a36Sopenharmony_ci count = -EINVAL; 4462306a36Sopenharmony_ci goto fail; 4562306a36Sopenharmony_ci } 4662306a36Sopenharmony_ci 4762306a36Sopenharmony_ci hdev->asic_prop.max_freq_value = value * 1000 * 1000; 4862306a36Sopenharmony_ci 4962306a36Sopenharmony_ci hl_fw_set_frequency(hdev, hdev->asic_prop.clk_pll_index, hdev->asic_prop.max_freq_value); 5062306a36Sopenharmony_ci 5162306a36Sopenharmony_cifail: 5262306a36Sopenharmony_ci return count; 5362306a36Sopenharmony_ci} 5462306a36Sopenharmony_ci 5562306a36Sopenharmony_cistatic ssize_t clk_cur_freq_mhz_show(struct device *dev, struct device_attribute *attr, char *buf) 5662306a36Sopenharmony_ci{ 5762306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 5862306a36Sopenharmony_ci long value; 5962306a36Sopenharmony_ci 6062306a36Sopenharmony_ci if (!hl_device_operational(hdev, NULL)) 6162306a36Sopenharmony_ci return -ENODEV; 6262306a36Sopenharmony_ci 6362306a36Sopenharmony_ci value = hl_fw_get_frequency(hdev, hdev->asic_prop.clk_pll_index, true); 6462306a36Sopenharmony_ci if (value < 0) 6562306a36Sopenharmony_ci return value; 6662306a36Sopenharmony_ci 6762306a36Sopenharmony_ci return sprintf(buf, "%lu\n", (value / 1000 / 1000)); 6862306a36Sopenharmony_ci} 6962306a36Sopenharmony_ci 7062306a36Sopenharmony_cistatic DEVICE_ATTR_RW(clk_max_freq_mhz); 7162306a36Sopenharmony_cistatic DEVICE_ATTR_RO(clk_cur_freq_mhz); 7262306a36Sopenharmony_ci 7362306a36Sopenharmony_cistatic struct attribute *hl_dev_clk_attrs[] = { 7462306a36Sopenharmony_ci &dev_attr_clk_max_freq_mhz.attr, 7562306a36Sopenharmony_ci &dev_attr_clk_cur_freq_mhz.attr, 7662306a36Sopenharmony_ci NULL, 7762306a36Sopenharmony_ci}; 7862306a36Sopenharmony_ci 7962306a36Sopenharmony_cistatic ssize_t vrm_ver_show(struct device *dev, struct device_attribute *attr, char *buf) 8062306a36Sopenharmony_ci{ 8162306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 8262306a36Sopenharmony_ci struct cpucp_info *cpucp_info; 8362306a36Sopenharmony_ci 8462306a36Sopenharmony_ci cpucp_info = &hdev->asic_prop.cpucp_info; 8562306a36Sopenharmony_ci 8662306a36Sopenharmony_ci if (cpucp_info->infineon_second_stage_version) 8762306a36Sopenharmony_ci return sprintf(buf, "%#04x %#04x\n", le32_to_cpu(cpucp_info->infineon_version), 8862306a36Sopenharmony_ci le32_to_cpu(cpucp_info->infineon_second_stage_version)); 8962306a36Sopenharmony_ci else 9062306a36Sopenharmony_ci return sprintf(buf, "%#04x\n", le32_to_cpu(cpucp_info->infineon_version)); 9162306a36Sopenharmony_ci} 9262306a36Sopenharmony_ci 9362306a36Sopenharmony_cistatic DEVICE_ATTR_RO(vrm_ver); 9462306a36Sopenharmony_ci 9562306a36Sopenharmony_cistatic struct attribute *hl_dev_vrm_attrs[] = { 9662306a36Sopenharmony_ci &dev_attr_vrm_ver.attr, 9762306a36Sopenharmony_ci NULL, 9862306a36Sopenharmony_ci}; 9962306a36Sopenharmony_ci 10062306a36Sopenharmony_cistatic ssize_t uboot_ver_show(struct device *dev, struct device_attribute *attr, 10162306a36Sopenharmony_ci char *buf) 10262306a36Sopenharmony_ci{ 10362306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 10462306a36Sopenharmony_ci 10562306a36Sopenharmony_ci return sprintf(buf, "%s\n", hdev->asic_prop.uboot_ver); 10662306a36Sopenharmony_ci} 10762306a36Sopenharmony_ci 10862306a36Sopenharmony_cistatic ssize_t armcp_kernel_ver_show(struct device *dev, 10962306a36Sopenharmony_ci struct device_attribute *attr, char *buf) 11062306a36Sopenharmony_ci{ 11162306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 11262306a36Sopenharmony_ci 11362306a36Sopenharmony_ci return sprintf(buf, "%s", hdev->asic_prop.cpucp_info.kernel_version); 11462306a36Sopenharmony_ci} 11562306a36Sopenharmony_ci 11662306a36Sopenharmony_cistatic ssize_t armcp_ver_show(struct device *dev, struct device_attribute *attr, 11762306a36Sopenharmony_ci char *buf) 11862306a36Sopenharmony_ci{ 11962306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 12062306a36Sopenharmony_ci 12162306a36Sopenharmony_ci return sprintf(buf, "%s\n", hdev->asic_prop.cpucp_info.cpucp_version); 12262306a36Sopenharmony_ci} 12362306a36Sopenharmony_ci 12462306a36Sopenharmony_cistatic ssize_t cpld_ver_show(struct device *dev, struct device_attribute *attr, 12562306a36Sopenharmony_ci char *buf) 12662306a36Sopenharmony_ci{ 12762306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 12862306a36Sopenharmony_ci 12962306a36Sopenharmony_ci return sprintf(buf, "0x%08x\n", 13062306a36Sopenharmony_ci le32_to_cpu(hdev->asic_prop.cpucp_info.cpld_version)); 13162306a36Sopenharmony_ci} 13262306a36Sopenharmony_ci 13362306a36Sopenharmony_cistatic ssize_t cpucp_kernel_ver_show(struct device *dev, 13462306a36Sopenharmony_ci struct device_attribute *attr, char *buf) 13562306a36Sopenharmony_ci{ 13662306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 13762306a36Sopenharmony_ci 13862306a36Sopenharmony_ci return sprintf(buf, "%s", hdev->asic_prop.cpucp_info.kernel_version); 13962306a36Sopenharmony_ci} 14062306a36Sopenharmony_ci 14162306a36Sopenharmony_cistatic ssize_t cpucp_ver_show(struct device *dev, struct device_attribute *attr, 14262306a36Sopenharmony_ci char *buf) 14362306a36Sopenharmony_ci{ 14462306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 14562306a36Sopenharmony_ci 14662306a36Sopenharmony_ci return sprintf(buf, "%s\n", hdev->asic_prop.cpucp_info.cpucp_version); 14762306a36Sopenharmony_ci} 14862306a36Sopenharmony_ci 14962306a36Sopenharmony_cistatic ssize_t fuse_ver_show(struct device *dev, struct device_attribute *attr, 15062306a36Sopenharmony_ci char *buf) 15162306a36Sopenharmony_ci{ 15262306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 15362306a36Sopenharmony_ci 15462306a36Sopenharmony_ci return sprintf(buf, "%s\n", hdev->asic_prop.cpucp_info.fuse_version); 15562306a36Sopenharmony_ci} 15662306a36Sopenharmony_ci 15762306a36Sopenharmony_cistatic ssize_t thermal_ver_show(struct device *dev, 15862306a36Sopenharmony_ci struct device_attribute *attr, char *buf) 15962306a36Sopenharmony_ci{ 16062306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 16162306a36Sopenharmony_ci 16262306a36Sopenharmony_ci return sprintf(buf, "%s", hdev->asic_prop.cpucp_info.thermal_version); 16362306a36Sopenharmony_ci} 16462306a36Sopenharmony_ci 16562306a36Sopenharmony_cistatic ssize_t fw_os_ver_show(struct device *dev, 16662306a36Sopenharmony_ci struct device_attribute *attr, char *buf) 16762306a36Sopenharmony_ci{ 16862306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 16962306a36Sopenharmony_ci 17062306a36Sopenharmony_ci return sprintf(buf, "%s", hdev->asic_prop.cpucp_info.fw_os_version); 17162306a36Sopenharmony_ci} 17262306a36Sopenharmony_ci 17362306a36Sopenharmony_cistatic ssize_t preboot_btl_ver_show(struct device *dev, 17462306a36Sopenharmony_ci struct device_attribute *attr, char *buf) 17562306a36Sopenharmony_ci{ 17662306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 17762306a36Sopenharmony_ci 17862306a36Sopenharmony_ci return sprintf(buf, "%s\n", hdev->asic_prop.preboot_ver); 17962306a36Sopenharmony_ci} 18062306a36Sopenharmony_ci 18162306a36Sopenharmony_cistatic ssize_t soft_reset_store(struct device *dev, 18262306a36Sopenharmony_ci struct device_attribute *attr, const char *buf, 18362306a36Sopenharmony_ci size_t count) 18462306a36Sopenharmony_ci{ 18562306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 18662306a36Sopenharmony_ci long value; 18762306a36Sopenharmony_ci int rc; 18862306a36Sopenharmony_ci 18962306a36Sopenharmony_ci rc = kstrtoul(buf, 0, &value); 19062306a36Sopenharmony_ci 19162306a36Sopenharmony_ci if (rc) { 19262306a36Sopenharmony_ci count = -EINVAL; 19362306a36Sopenharmony_ci goto out; 19462306a36Sopenharmony_ci } 19562306a36Sopenharmony_ci 19662306a36Sopenharmony_ci if (!hdev->asic_prop.allow_inference_soft_reset) { 19762306a36Sopenharmony_ci dev_err(hdev->dev, "Device does not support inference soft-reset\n"); 19862306a36Sopenharmony_ci goto out; 19962306a36Sopenharmony_ci } 20062306a36Sopenharmony_ci 20162306a36Sopenharmony_ci dev_warn(hdev->dev, "Inference Soft-Reset requested through sysfs\n"); 20262306a36Sopenharmony_ci 20362306a36Sopenharmony_ci hl_device_reset(hdev, 0); 20462306a36Sopenharmony_ci 20562306a36Sopenharmony_ciout: 20662306a36Sopenharmony_ci return count; 20762306a36Sopenharmony_ci} 20862306a36Sopenharmony_ci 20962306a36Sopenharmony_cistatic ssize_t hard_reset_store(struct device *dev, 21062306a36Sopenharmony_ci struct device_attribute *attr, 21162306a36Sopenharmony_ci const char *buf, size_t count) 21262306a36Sopenharmony_ci{ 21362306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 21462306a36Sopenharmony_ci long value; 21562306a36Sopenharmony_ci int rc; 21662306a36Sopenharmony_ci 21762306a36Sopenharmony_ci rc = kstrtoul(buf, 0, &value); 21862306a36Sopenharmony_ci 21962306a36Sopenharmony_ci if (rc) { 22062306a36Sopenharmony_ci count = -EINVAL; 22162306a36Sopenharmony_ci goto out; 22262306a36Sopenharmony_ci } 22362306a36Sopenharmony_ci 22462306a36Sopenharmony_ci dev_warn(hdev->dev, "Hard-Reset requested through sysfs\n"); 22562306a36Sopenharmony_ci 22662306a36Sopenharmony_ci hl_device_reset(hdev, HL_DRV_RESET_HARD); 22762306a36Sopenharmony_ci 22862306a36Sopenharmony_ciout: 22962306a36Sopenharmony_ci return count; 23062306a36Sopenharmony_ci} 23162306a36Sopenharmony_ci 23262306a36Sopenharmony_cistatic ssize_t device_type_show(struct device *dev, 23362306a36Sopenharmony_ci struct device_attribute *attr, char *buf) 23462306a36Sopenharmony_ci{ 23562306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 23662306a36Sopenharmony_ci char *str; 23762306a36Sopenharmony_ci 23862306a36Sopenharmony_ci switch (hdev->asic_type) { 23962306a36Sopenharmony_ci case ASIC_GOYA: 24062306a36Sopenharmony_ci str = "GOYA"; 24162306a36Sopenharmony_ci break; 24262306a36Sopenharmony_ci case ASIC_GAUDI: 24362306a36Sopenharmony_ci str = "GAUDI"; 24462306a36Sopenharmony_ci break; 24562306a36Sopenharmony_ci case ASIC_GAUDI_SEC: 24662306a36Sopenharmony_ci str = "GAUDI SEC"; 24762306a36Sopenharmony_ci break; 24862306a36Sopenharmony_ci case ASIC_GAUDI2: 24962306a36Sopenharmony_ci str = "GAUDI2"; 25062306a36Sopenharmony_ci break; 25162306a36Sopenharmony_ci case ASIC_GAUDI2B: 25262306a36Sopenharmony_ci str = "GAUDI2B"; 25362306a36Sopenharmony_ci break; 25462306a36Sopenharmony_ci case ASIC_GAUDI2C: 25562306a36Sopenharmony_ci str = "GAUDI2C"; 25662306a36Sopenharmony_ci break; 25762306a36Sopenharmony_ci default: 25862306a36Sopenharmony_ci dev_err(hdev->dev, "Unrecognized ASIC type %d\n", 25962306a36Sopenharmony_ci hdev->asic_type); 26062306a36Sopenharmony_ci return -EINVAL; 26162306a36Sopenharmony_ci } 26262306a36Sopenharmony_ci 26362306a36Sopenharmony_ci return sprintf(buf, "%s\n", str); 26462306a36Sopenharmony_ci} 26562306a36Sopenharmony_ci 26662306a36Sopenharmony_cistatic ssize_t pci_addr_show(struct device *dev, struct device_attribute *attr, 26762306a36Sopenharmony_ci char *buf) 26862306a36Sopenharmony_ci{ 26962306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 27062306a36Sopenharmony_ci 27162306a36Sopenharmony_ci return sprintf(buf, "%04x:%02x:%02x.%x\n", 27262306a36Sopenharmony_ci pci_domain_nr(hdev->pdev->bus), 27362306a36Sopenharmony_ci hdev->pdev->bus->number, 27462306a36Sopenharmony_ci PCI_SLOT(hdev->pdev->devfn), 27562306a36Sopenharmony_ci PCI_FUNC(hdev->pdev->devfn)); 27662306a36Sopenharmony_ci} 27762306a36Sopenharmony_ci 27862306a36Sopenharmony_cistatic ssize_t status_show(struct device *dev, struct device_attribute *attr, 27962306a36Sopenharmony_ci char *buf) 28062306a36Sopenharmony_ci{ 28162306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 28262306a36Sopenharmony_ci char str[HL_STR_MAX]; 28362306a36Sopenharmony_ci 28462306a36Sopenharmony_ci strscpy(str, hdev->status[hl_device_status(hdev)], HL_STR_MAX); 28562306a36Sopenharmony_ci 28662306a36Sopenharmony_ci /* use uppercase for backward compatibility */ 28762306a36Sopenharmony_ci str[0] = 'A' + (str[0] - 'a'); 28862306a36Sopenharmony_ci 28962306a36Sopenharmony_ci return sprintf(buf, "%s\n", str); 29062306a36Sopenharmony_ci} 29162306a36Sopenharmony_ci 29262306a36Sopenharmony_cistatic ssize_t soft_reset_cnt_show(struct device *dev, 29362306a36Sopenharmony_ci struct device_attribute *attr, char *buf) 29462306a36Sopenharmony_ci{ 29562306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 29662306a36Sopenharmony_ci 29762306a36Sopenharmony_ci return sprintf(buf, "%d\n", hdev->reset_info.compute_reset_cnt); 29862306a36Sopenharmony_ci} 29962306a36Sopenharmony_ci 30062306a36Sopenharmony_cistatic ssize_t hard_reset_cnt_show(struct device *dev, 30162306a36Sopenharmony_ci struct device_attribute *attr, char *buf) 30262306a36Sopenharmony_ci{ 30362306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 30462306a36Sopenharmony_ci 30562306a36Sopenharmony_ci return sprintf(buf, "%d\n", hdev->reset_info.hard_reset_cnt); 30662306a36Sopenharmony_ci} 30762306a36Sopenharmony_ci 30862306a36Sopenharmony_cistatic ssize_t max_power_show(struct device *dev, struct device_attribute *attr, 30962306a36Sopenharmony_ci char *buf) 31062306a36Sopenharmony_ci{ 31162306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 31262306a36Sopenharmony_ci long val; 31362306a36Sopenharmony_ci 31462306a36Sopenharmony_ci if (!hl_device_operational(hdev, NULL)) 31562306a36Sopenharmony_ci return -ENODEV; 31662306a36Sopenharmony_ci 31762306a36Sopenharmony_ci val = hl_fw_get_max_power(hdev); 31862306a36Sopenharmony_ci if (val < 0) 31962306a36Sopenharmony_ci return val; 32062306a36Sopenharmony_ci 32162306a36Sopenharmony_ci return sprintf(buf, "%lu\n", val); 32262306a36Sopenharmony_ci} 32362306a36Sopenharmony_ci 32462306a36Sopenharmony_cistatic ssize_t max_power_store(struct device *dev, 32562306a36Sopenharmony_ci struct device_attribute *attr, const char *buf, size_t count) 32662306a36Sopenharmony_ci{ 32762306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 32862306a36Sopenharmony_ci unsigned long value; 32962306a36Sopenharmony_ci int rc; 33062306a36Sopenharmony_ci 33162306a36Sopenharmony_ci if (!hl_device_operational(hdev, NULL)) { 33262306a36Sopenharmony_ci count = -ENODEV; 33362306a36Sopenharmony_ci goto out; 33462306a36Sopenharmony_ci } 33562306a36Sopenharmony_ci 33662306a36Sopenharmony_ci rc = kstrtoul(buf, 0, &value); 33762306a36Sopenharmony_ci 33862306a36Sopenharmony_ci if (rc) { 33962306a36Sopenharmony_ci count = -EINVAL; 34062306a36Sopenharmony_ci goto out; 34162306a36Sopenharmony_ci } 34262306a36Sopenharmony_ci 34362306a36Sopenharmony_ci hdev->max_power = value; 34462306a36Sopenharmony_ci hl_fw_set_max_power(hdev); 34562306a36Sopenharmony_ci 34662306a36Sopenharmony_ciout: 34762306a36Sopenharmony_ci return count; 34862306a36Sopenharmony_ci} 34962306a36Sopenharmony_ci 35062306a36Sopenharmony_cistatic ssize_t eeprom_read_handler(struct file *filp, struct kobject *kobj, 35162306a36Sopenharmony_ci struct bin_attribute *attr, char *buf, loff_t offset, 35262306a36Sopenharmony_ci size_t max_size) 35362306a36Sopenharmony_ci{ 35462306a36Sopenharmony_ci struct device *dev = kobj_to_dev(kobj); 35562306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 35662306a36Sopenharmony_ci char *data; 35762306a36Sopenharmony_ci int rc; 35862306a36Sopenharmony_ci 35962306a36Sopenharmony_ci if (!hl_device_operational(hdev, NULL)) 36062306a36Sopenharmony_ci return -ENODEV; 36162306a36Sopenharmony_ci 36262306a36Sopenharmony_ci if (!max_size) 36362306a36Sopenharmony_ci return -EINVAL; 36462306a36Sopenharmony_ci 36562306a36Sopenharmony_ci data = kzalloc(max_size, GFP_KERNEL); 36662306a36Sopenharmony_ci if (!data) 36762306a36Sopenharmony_ci return -ENOMEM; 36862306a36Sopenharmony_ci 36962306a36Sopenharmony_ci rc = hdev->asic_funcs->get_eeprom_data(hdev, data, max_size); 37062306a36Sopenharmony_ci if (rc) 37162306a36Sopenharmony_ci goto out; 37262306a36Sopenharmony_ci 37362306a36Sopenharmony_ci memcpy(buf, data, max_size); 37462306a36Sopenharmony_ci 37562306a36Sopenharmony_ciout: 37662306a36Sopenharmony_ci kfree(data); 37762306a36Sopenharmony_ci 37862306a36Sopenharmony_ci return max_size; 37962306a36Sopenharmony_ci} 38062306a36Sopenharmony_ci 38162306a36Sopenharmony_cistatic ssize_t security_enabled_show(struct device *dev, 38262306a36Sopenharmony_ci struct device_attribute *attr, char *buf) 38362306a36Sopenharmony_ci{ 38462306a36Sopenharmony_ci struct hl_device *hdev = dev_get_drvdata(dev); 38562306a36Sopenharmony_ci 38662306a36Sopenharmony_ci return sprintf(buf, "%d\n", hdev->asic_prop.fw_security_enabled); 38762306a36Sopenharmony_ci} 38862306a36Sopenharmony_ci 38962306a36Sopenharmony_cistatic DEVICE_ATTR_RO(armcp_kernel_ver); 39062306a36Sopenharmony_cistatic DEVICE_ATTR_RO(armcp_ver); 39162306a36Sopenharmony_cistatic DEVICE_ATTR_RO(cpld_ver); 39262306a36Sopenharmony_cistatic DEVICE_ATTR_RO(cpucp_kernel_ver); 39362306a36Sopenharmony_cistatic DEVICE_ATTR_RO(cpucp_ver); 39462306a36Sopenharmony_cistatic DEVICE_ATTR_RO(device_type); 39562306a36Sopenharmony_cistatic DEVICE_ATTR_RO(fuse_ver); 39662306a36Sopenharmony_cistatic DEVICE_ATTR_WO(hard_reset); 39762306a36Sopenharmony_cistatic DEVICE_ATTR_RO(hard_reset_cnt); 39862306a36Sopenharmony_cistatic DEVICE_ATTR_RW(max_power); 39962306a36Sopenharmony_cistatic DEVICE_ATTR_RO(pci_addr); 40062306a36Sopenharmony_cistatic DEVICE_ATTR_RO(preboot_btl_ver); 40162306a36Sopenharmony_cistatic DEVICE_ATTR_WO(soft_reset); 40262306a36Sopenharmony_cistatic DEVICE_ATTR_RO(soft_reset_cnt); 40362306a36Sopenharmony_cistatic DEVICE_ATTR_RO(status); 40462306a36Sopenharmony_cistatic DEVICE_ATTR_RO(thermal_ver); 40562306a36Sopenharmony_cistatic DEVICE_ATTR_RO(uboot_ver); 40662306a36Sopenharmony_cistatic DEVICE_ATTR_RO(fw_os_ver); 40762306a36Sopenharmony_cistatic DEVICE_ATTR_RO(security_enabled); 40862306a36Sopenharmony_ci 40962306a36Sopenharmony_cistatic struct bin_attribute bin_attr_eeprom = { 41062306a36Sopenharmony_ci .attr = {.name = "eeprom", .mode = (0444)}, 41162306a36Sopenharmony_ci .size = PAGE_SIZE, 41262306a36Sopenharmony_ci .read = eeprom_read_handler 41362306a36Sopenharmony_ci}; 41462306a36Sopenharmony_ci 41562306a36Sopenharmony_cistatic struct attribute *hl_dev_attrs[] = { 41662306a36Sopenharmony_ci &dev_attr_armcp_kernel_ver.attr, 41762306a36Sopenharmony_ci &dev_attr_armcp_ver.attr, 41862306a36Sopenharmony_ci &dev_attr_cpld_ver.attr, 41962306a36Sopenharmony_ci &dev_attr_cpucp_kernel_ver.attr, 42062306a36Sopenharmony_ci &dev_attr_cpucp_ver.attr, 42162306a36Sopenharmony_ci &dev_attr_device_type.attr, 42262306a36Sopenharmony_ci &dev_attr_fuse_ver.attr, 42362306a36Sopenharmony_ci &dev_attr_hard_reset.attr, 42462306a36Sopenharmony_ci &dev_attr_hard_reset_cnt.attr, 42562306a36Sopenharmony_ci &dev_attr_max_power.attr, 42662306a36Sopenharmony_ci &dev_attr_pci_addr.attr, 42762306a36Sopenharmony_ci &dev_attr_preboot_btl_ver.attr, 42862306a36Sopenharmony_ci &dev_attr_status.attr, 42962306a36Sopenharmony_ci &dev_attr_thermal_ver.attr, 43062306a36Sopenharmony_ci &dev_attr_uboot_ver.attr, 43162306a36Sopenharmony_ci &dev_attr_fw_os_ver.attr, 43262306a36Sopenharmony_ci &dev_attr_security_enabled.attr, 43362306a36Sopenharmony_ci NULL, 43462306a36Sopenharmony_ci}; 43562306a36Sopenharmony_ci 43662306a36Sopenharmony_cistatic struct bin_attribute *hl_dev_bin_attrs[] = { 43762306a36Sopenharmony_ci &bin_attr_eeprom, 43862306a36Sopenharmony_ci NULL 43962306a36Sopenharmony_ci}; 44062306a36Sopenharmony_ci 44162306a36Sopenharmony_cistatic struct attribute_group hl_dev_attr_group = { 44262306a36Sopenharmony_ci .attrs = hl_dev_attrs, 44362306a36Sopenharmony_ci .bin_attrs = hl_dev_bin_attrs, 44462306a36Sopenharmony_ci}; 44562306a36Sopenharmony_ci 44662306a36Sopenharmony_cistatic struct attribute_group hl_dev_clks_attr_group; 44762306a36Sopenharmony_cistatic struct attribute_group hl_dev_vrm_attr_group; 44862306a36Sopenharmony_ci 44962306a36Sopenharmony_cistatic const struct attribute_group *hl_dev_attr_groups[] = { 45062306a36Sopenharmony_ci &hl_dev_attr_group, 45162306a36Sopenharmony_ci &hl_dev_clks_attr_group, 45262306a36Sopenharmony_ci &hl_dev_vrm_attr_group, 45362306a36Sopenharmony_ci NULL, 45462306a36Sopenharmony_ci}; 45562306a36Sopenharmony_ci 45662306a36Sopenharmony_cistatic struct attribute *hl_dev_inference_attrs[] = { 45762306a36Sopenharmony_ci &dev_attr_soft_reset.attr, 45862306a36Sopenharmony_ci &dev_attr_soft_reset_cnt.attr, 45962306a36Sopenharmony_ci NULL, 46062306a36Sopenharmony_ci}; 46162306a36Sopenharmony_ci 46262306a36Sopenharmony_cistatic struct attribute_group hl_dev_inference_attr_group = { 46362306a36Sopenharmony_ci .attrs = hl_dev_inference_attrs, 46462306a36Sopenharmony_ci}; 46562306a36Sopenharmony_ci 46662306a36Sopenharmony_cistatic const struct attribute_group *hl_dev_inference_attr_groups[] = { 46762306a36Sopenharmony_ci &hl_dev_inference_attr_group, 46862306a36Sopenharmony_ci NULL, 46962306a36Sopenharmony_ci}; 47062306a36Sopenharmony_ci 47162306a36Sopenharmony_civoid hl_sysfs_add_dev_clk_attr(struct hl_device *hdev, struct attribute_group *dev_clk_attr_grp) 47262306a36Sopenharmony_ci{ 47362306a36Sopenharmony_ci dev_clk_attr_grp->attrs = hl_dev_clk_attrs; 47462306a36Sopenharmony_ci} 47562306a36Sopenharmony_ci 47662306a36Sopenharmony_civoid hl_sysfs_add_dev_vrm_attr(struct hl_device *hdev, struct attribute_group *dev_vrm_attr_grp) 47762306a36Sopenharmony_ci{ 47862306a36Sopenharmony_ci dev_vrm_attr_grp->attrs = hl_dev_vrm_attrs; 47962306a36Sopenharmony_ci} 48062306a36Sopenharmony_ci 48162306a36Sopenharmony_ciint hl_sysfs_init(struct hl_device *hdev) 48262306a36Sopenharmony_ci{ 48362306a36Sopenharmony_ci int rc; 48462306a36Sopenharmony_ci 48562306a36Sopenharmony_ci hdev->max_power = hdev->asic_prop.max_power_default; 48662306a36Sopenharmony_ci 48762306a36Sopenharmony_ci hdev->asic_funcs->add_device_attr(hdev, &hl_dev_clks_attr_group, &hl_dev_vrm_attr_group); 48862306a36Sopenharmony_ci 48962306a36Sopenharmony_ci rc = device_add_groups(hdev->dev, hl_dev_attr_groups); 49062306a36Sopenharmony_ci if (rc) { 49162306a36Sopenharmony_ci dev_err(hdev->dev, 49262306a36Sopenharmony_ci "Failed to add groups to device, error %d\n", rc); 49362306a36Sopenharmony_ci return rc; 49462306a36Sopenharmony_ci } 49562306a36Sopenharmony_ci 49662306a36Sopenharmony_ci if (!hdev->asic_prop.allow_inference_soft_reset) 49762306a36Sopenharmony_ci return 0; 49862306a36Sopenharmony_ci 49962306a36Sopenharmony_ci rc = device_add_groups(hdev->dev, hl_dev_inference_attr_groups); 50062306a36Sopenharmony_ci if (rc) { 50162306a36Sopenharmony_ci dev_err(hdev->dev, 50262306a36Sopenharmony_ci "Failed to add groups to device, error %d\n", rc); 50362306a36Sopenharmony_ci goto remove_groups; 50462306a36Sopenharmony_ci } 50562306a36Sopenharmony_ci 50662306a36Sopenharmony_ci return 0; 50762306a36Sopenharmony_ci 50862306a36Sopenharmony_ciremove_groups: 50962306a36Sopenharmony_ci device_remove_groups(hdev->dev, hl_dev_attr_groups); 51062306a36Sopenharmony_ci return rc; 51162306a36Sopenharmony_ci} 51262306a36Sopenharmony_ci 51362306a36Sopenharmony_civoid hl_sysfs_fini(struct hl_device *hdev) 51462306a36Sopenharmony_ci{ 51562306a36Sopenharmony_ci device_remove_groups(hdev->dev, hl_dev_attr_groups); 51662306a36Sopenharmony_ci 51762306a36Sopenharmony_ci if (!hdev->asic_prop.allow_inference_soft_reset) 51862306a36Sopenharmony_ci return; 51962306a36Sopenharmony_ci 52062306a36Sopenharmony_ci device_remove_groups(hdev->dev, hl_dev_inference_attr_groups); 52162306a36Sopenharmony_ci} 522