1 // SPDX-License-Identifier: GPL-2.0 2 /* Texas Instruments ICSSG Ethernet driver 3 * 4 * Copyright (C) 2018-2021 Texas Instruments Incorporated - https://www.ti.com/ 5 * 6 */ 7 8 #include "icssg_prueth.h" 9 #include "icssg_stats.h" 10 #include <linux/regmap.h> 11 12 static u32 stats_base[] = { 0x54c, /* Slice 0 stats start */ 13 0xb18, /* Slice 1 stats start */ 14 }; 15 16 void emac_update_hardware_stats(struct prueth_emac *emac) 17 { 18 struct prueth *prueth = emac->prueth; 19 int slice = prueth_emac_slice(emac); 20 u32 base = stats_base[slice]; 21 u32 val; 22 int i; 23 24 for (i = 0; i < ARRAY_SIZE(icssg_all_stats); i++) { 25 regmap_read(prueth->miig_rt, 26 base + icssg_all_stats[i].offset, 27 &val); 28 regmap_write(prueth->miig_rt, 29 base + icssg_all_stats[i].offset, 30 val); 31 32 emac->stats[i] += val; 33 } 34 } 35 36 void emac_stats_work_handler(struct work_struct *work) 37 { 38 struct prueth_emac *emac = container_of(work, struct prueth_emac, 39 stats_work.work); 40 emac_update_hardware_stats(emac); 41 42 queue_delayed_work(system_long_wq, &emac->stats_work, 43 msecs_to_jiffies((STATS_TIME_LIMIT_1G_MS * 1000) / emac->speed)); 44 } 45 46 int emac_get_stat_by_name(struct prueth_emac *emac, char *stat_name) 47 { 48 int i; 49 50 for (i = 0; i < ARRAY_SIZE(icssg_all_stats); i++) { 51 if (!strcmp(icssg_all_stats[i].name, stat_name)) 52 return emac->stats[icssg_all_stats[i].offset / sizeof(u32)]; 53 } 54 55 netdev_err(emac->ndev, "Invalid stats %s\n", stat_name); 56 return -EINVAL; 57 } 58