158 lines
		
	
	
		
			3.7 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
			
		
		
	
	
			158 lines
		
	
	
		
			3.7 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
// SPDX-License-Identifier: GPL-2.0
 | 
						|
/*
 | 
						|
 * Debugfs interface Support for MPT (Message Passing Technology) based
 | 
						|
 * controllers.
 | 
						|
 *
 | 
						|
 * Copyright (C) 2020  Broadcom Inc.
 | 
						|
 *
 | 
						|
 * Authors: Broadcom Inc.
 | 
						|
 * Sreekanth Reddy  <sreekanth.reddy@broadcom.com>
 | 
						|
 * Suganath Prabu <suganath-prabu.subramani@broadcom.com>
 | 
						|
 *
 | 
						|
 * Send feedback to : MPT-FusionLinux.pdl@broadcom.com)
 | 
						|
 *
 | 
						|
 **/
 | 
						|
 | 
						|
#include <linux/kernel.h>
 | 
						|
#include <linux/types.h>
 | 
						|
#include <linux/pci.h>
 | 
						|
#include <linux/interrupt.h>
 | 
						|
#include <linux/compat.h>
 | 
						|
#include <linux/uio.h>
 | 
						|
 | 
						|
#include <scsi/scsi.h>
 | 
						|
#include <scsi/scsi_device.h>
 | 
						|
#include <scsi/scsi_host.h>
 | 
						|
#include "mpt3sas_base.h"
 | 
						|
#include <linux/debugfs.h>
 | 
						|
 | 
						|
static struct dentry *mpt3sas_debugfs_root;
 | 
						|
 | 
						|
/*
 | 
						|
 * _debugfs_iocdump_read - copy ioc dump from debugfs buffer
 | 
						|
 * @filep:	File Pointer
 | 
						|
 * @ubuf:	Buffer to fill data
 | 
						|
 * @cnt:	Length of the buffer
 | 
						|
 * @ppos:	Offset in the file
 | 
						|
 */
 | 
						|
 | 
						|
static ssize_t
 | 
						|
_debugfs_iocdump_read(struct file *filp, char __user *ubuf, size_t cnt,
 | 
						|
	loff_t *ppos)
 | 
						|
 | 
						|
{
 | 
						|
	struct mpt3sas_debugfs_buffer *debug = filp->private_data;
 | 
						|
 | 
						|
	if (!debug || !debug->buf)
 | 
						|
		return 0;
 | 
						|
 | 
						|
	return simple_read_from_buffer(ubuf, cnt, ppos, debug->buf, debug->len);
 | 
						|
}
 | 
						|
 | 
						|
/*
 | 
						|
 * _debugfs_iocdump_open :	open the ioc_dump debugfs attribute file
 | 
						|
 */
 | 
						|
static int
 | 
						|
_debugfs_iocdump_open(struct inode *inode, struct file *file)
 | 
						|
{
 | 
						|
	struct MPT3SAS_ADAPTER *ioc = inode->i_private;
 | 
						|
	struct mpt3sas_debugfs_buffer *debug;
 | 
						|
 | 
						|
	debug = kzalloc(sizeof(struct mpt3sas_debugfs_buffer), GFP_KERNEL);
 | 
						|
	if (!debug)
 | 
						|
		return -ENOMEM;
 | 
						|
 | 
						|
	debug->buf = (void *)ioc;
 | 
						|
	debug->len = sizeof(struct MPT3SAS_ADAPTER);
 | 
						|
	file->private_data = debug;
 | 
						|
	return 0;
 | 
						|
}
 | 
						|
 | 
						|
/*
 | 
						|
 * _debugfs_iocdump_release :	release the ioc_dump debugfs attribute
 | 
						|
 * @inode: inode structure to the corresponds device
 | 
						|
 * @file: File pointer
 | 
						|
 */
 | 
						|
static int
 | 
						|
_debugfs_iocdump_release(struct inode *inode, struct file *file)
 | 
						|
{
 | 
						|
	struct mpt3sas_debugfs_buffer *debug = file->private_data;
 | 
						|
 | 
						|
	if (!debug)
 | 
						|
		return 0;
 | 
						|
 | 
						|
	file->private_data = NULL;
 | 
						|
	kfree(debug);
 | 
						|
	return 0;
 | 
						|
}
 | 
						|
 | 
						|
static const struct file_operations mpt3sas_debugfs_iocdump_fops = {
 | 
						|
	.owner		= THIS_MODULE,
 | 
						|
	.open           = _debugfs_iocdump_open,
 | 
						|
	.read           = _debugfs_iocdump_read,
 | 
						|
	.release        = _debugfs_iocdump_release,
 | 
						|
};
 | 
						|
 | 
						|
/*
 | 
						|
 * mpt3sas_init_debugfs :	Create debugfs root for mpt3sas driver
 | 
						|
 */
 | 
						|
void mpt3sas_init_debugfs(void)
 | 
						|
{
 | 
						|
	mpt3sas_debugfs_root = debugfs_create_dir("mpt3sas", NULL);
 | 
						|
	if (!mpt3sas_debugfs_root)
 | 
						|
		pr_info("mpt3sas: Cannot create debugfs root\n");
 | 
						|
}
 | 
						|
 | 
						|
/*
 | 
						|
 * mpt3sas_exit_debugfs :	Remove debugfs root for mpt3sas driver
 | 
						|
 */
 | 
						|
void mpt3sas_exit_debugfs(void)
 | 
						|
{
 | 
						|
	debugfs_remove_recursive(mpt3sas_debugfs_root);
 | 
						|
}
 | 
						|
 | 
						|
/*
 | 
						|
 * mpt3sas_setup_debugfs :	Setup debugfs per HBA adapter
 | 
						|
 * ioc:				MPT3SAS_ADAPTER object
 | 
						|
 */
 | 
						|
void
 | 
						|
mpt3sas_setup_debugfs(struct MPT3SAS_ADAPTER *ioc)
 | 
						|
{
 | 
						|
	char name[64];
 | 
						|
 | 
						|
	snprintf(name, sizeof(name), "scsi_host%d", ioc->shost->host_no);
 | 
						|
	if (!ioc->debugfs_root) {
 | 
						|
		ioc->debugfs_root =
 | 
						|
		    debugfs_create_dir(name, mpt3sas_debugfs_root);
 | 
						|
		if (!ioc->debugfs_root) {
 | 
						|
			dev_err(&ioc->pdev->dev,
 | 
						|
			    "Cannot create per adapter debugfs directory\n");
 | 
						|
			return;
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
	snprintf(name, sizeof(name), "ioc_dump");
 | 
						|
	ioc->ioc_dump =	debugfs_create_file(name, 0444,
 | 
						|
	    ioc->debugfs_root, ioc, &mpt3sas_debugfs_iocdump_fops);
 | 
						|
	if (!ioc->ioc_dump) {
 | 
						|
		dev_err(&ioc->pdev->dev,
 | 
						|
		    "Cannot create ioc_dump debugfs file\n");
 | 
						|
		debugfs_remove(ioc->debugfs_root);
 | 
						|
		return;
 | 
						|
	}
 | 
						|
 | 
						|
	snprintf(name, sizeof(name), "host_recovery");
 | 
						|
	debugfs_create_u8(name, 0444, ioc->debugfs_root, &ioc->shost_recovery);
 | 
						|
 | 
						|
}
 | 
						|
 | 
						|
/*
 | 
						|
 * mpt3sas_destroy_debugfs :	Destroy debugfs per HBA adapter
 | 
						|
 * @ioc:	MPT3SAS_ADAPTER object
 | 
						|
 */
 | 
						|
void mpt3sas_destroy_debugfs(struct MPT3SAS_ADAPTER *ioc)
 | 
						|
{
 | 
						|
	debugfs_remove_recursive(ioc->debugfs_root);
 | 
						|
}
 | 
						|
 |