1 // SPDX-License-Identifier: GPL-2.0 2 /* Copyright (c) 2019 Mellanox Technologies. All rights reserved */ 3 4 #include <linux/debugfs.h> 5 #include <linux/err.h> 6 #include <linux/kernel.h> 7 #include <linux/slab.h> 8 9 #include "netdevsim.h" 10 11 static struct dentry *nsim_sdev_ddir; 12 13 static u32 nsim_sdev_id; 14 nsim_sdev_get(struct netdevsim * joinns)15struct netdevsim_shared_dev *nsim_sdev_get(struct netdevsim *joinns) 16 { 17 struct netdevsim_shared_dev *sdev; 18 char sdev_ddir_name[10]; 19 int err; 20 21 if (joinns) { 22 if (WARN_ON(!joinns->sdev)) 23 return ERR_PTR(-EINVAL); 24 sdev = joinns->sdev; 25 sdev->refcnt++; 26 return sdev; 27 } 28 29 sdev = kzalloc(sizeof(*sdev), GFP_KERNEL); 30 if (!sdev) 31 return ERR_PTR(-ENOMEM); 32 sdev->refcnt = 1; 33 sdev->switch_id = nsim_sdev_id++; 34 35 sprintf(sdev_ddir_name, "%u", sdev->switch_id); 36 sdev->ddir = debugfs_create_dir(sdev_ddir_name, nsim_sdev_ddir); 37 if (IS_ERR_OR_NULL(sdev->ddir)) { 38 err = PTR_ERR_OR_ZERO(sdev->ddir) ?: -EINVAL; 39 goto err_sdev_free; 40 } 41 42 return sdev; 43 44 err_sdev_free: 45 nsim_sdev_id--; 46 kfree(sdev); 47 return ERR_PTR(err); 48 } 49 nsim_sdev_put(struct netdevsim_shared_dev * sdev)50void nsim_sdev_put(struct netdevsim_shared_dev *sdev) 51 { 52 if (--sdev->refcnt) 53 return; 54 debugfs_remove_recursive(sdev->ddir); 55 kfree(sdev); 56 } 57 nsim_sdev_init(void)58int nsim_sdev_init(void) 59 { 60 nsim_sdev_ddir = debugfs_create_dir(DRV_NAME "_sdev", NULL); 61 if (IS_ERR_OR_NULL(nsim_sdev_ddir)) 62 return -ENOMEM; 63 return 0; 64 } 65 nsim_sdev_exit(void)66void nsim_sdev_exit(void) 67 { 68 debugfs_remove_recursive(nsim_sdev_ddir); 69 } 70