summaryrefslogtreecommitdiffstats
path: root/kernel/drivers/net/wireless/brcm80211/brcmfmac/debug.c
diff options
context:
space:
mode:
Diffstat (limited to 'kernel/drivers/net/wireless/brcm80211/brcmfmac/debug.c')
-rw-r--r--kernel/drivers/net/wireless/brcm80211/brcmfmac/debug.c92
1 files changed, 43 insertions, 49 deletions
diff --git a/kernel/drivers/net/wireless/brcm80211/brcmfmac/debug.c b/kernel/drivers/net/wireless/brcm80211/brcmfmac/debug.c
index 9b473d50b..1299dccc7 100644
--- a/kernel/drivers/net/wireless/brcm80211/brcmfmac/debug.c
+++ b/kernel/drivers/net/wireless/brcm80211/brcmfmac/debug.c
@@ -16,15 +16,45 @@
#include <linux/debugfs.h>
#include <linux/netdevice.h>
#include <linux/module.h>
+#include <linux/devcoredump.h>
#include <brcmu_wifi.h>
#include <brcmu_utils.h>
#include "core.h"
#include "bus.h"
+#include "fweh.h"
#include "debug.h"
static struct dentry *root_folder;
+static int brcmf_debug_create_memdump(struct brcmf_bus *bus, const void *data,
+ size_t len)
+{
+ void *dump;
+ size_t ramsize;
+
+ ramsize = brcmf_bus_get_ramsize(bus);
+ if (ramsize) {
+ dump = vzalloc(len + ramsize);
+ if (!dump)
+ return -ENOMEM;
+ memcpy(dump, data, len);
+ brcmf_bus_get_memdump(bus, dump + len, ramsize);
+ dev_coredumpv(bus->dev, dump, len + ramsize, GFP_KERNEL);
+ }
+ return 0;
+}
+
+static int brcmf_debug_psm_watchdog_notify(struct brcmf_if *ifp,
+ const struct brcmf_event_msg *evtmsg,
+ void *data)
+{
+ brcmf_dbg(TRACE, "enter: idx=%d\n", ifp->bssidx);
+
+ return brcmf_debug_create_memdump(ifp->drvr->bus_if, data,
+ evtmsg->datalen);
+}
+
void brcmf_debugfs_init(void)
{
root_folder = debugfs_create_dir(KBUILD_MODNAME, NULL);
@@ -41,16 +71,7 @@ void brcmf_debugfs_exit(void)
root_folder = NULL;
}
-static int brcmf_debugfs_chipinfo_read(struct seq_file *seq, void *data)
-{
- struct brcmf_bus *bus = dev_get_drvdata(seq->private);
-
- seq_printf(seq, "chip: %x(%u) rev %u\n",
- bus->chip, bus->chip, bus->chiprev);
- return 0;
-}
-
-int brcmf_debugfs_attach(struct brcmf_pub *drvr)
+int brcmf_debug_attach(struct brcmf_pub *drvr)
{
struct device *dev = drvr->bus_if->dev;
@@ -58,13 +79,18 @@ int brcmf_debugfs_attach(struct brcmf_pub *drvr)
return -ENODEV;
drvr->dbgfs_dir = debugfs_create_dir(dev_name(dev), root_folder);
- brcmf_debugfs_add_entry(drvr, "chipinfo", brcmf_debugfs_chipinfo_read);
+ if (IS_ERR(drvr->dbgfs_dir))
+ return PTR_ERR(drvr->dbgfs_dir);
- return PTR_ERR_OR_ZERO(drvr->dbgfs_dir);
+
+ return brcmf_fweh_register(drvr, BRCMF_E_PSM_WATCHDOG,
+ brcmf_debug_psm_watchdog_notify);
}
-void brcmf_debugfs_detach(struct brcmf_pub *drvr)
+void brcmf_debug_detach(struct brcmf_pub *drvr)
{
+ brcmf_fweh_unregister(drvr, BRCMF_E_PSM_WATCHDOG);
+
if (!IS_ERR_OR_NULL(drvr->dbgfs_dir))
debugfs_remove_recursive(drvr->dbgfs_dir);
}
@@ -74,44 +100,12 @@ struct dentry *brcmf_debugfs_get_devdir(struct brcmf_pub *drvr)
return drvr->dbgfs_dir;
}
-struct brcmf_debugfs_entry {
- int (*read)(struct seq_file *seq, void *data);
- struct brcmf_pub *drvr;
-};
-
-static int brcmf_debugfs_entry_open(struct inode *inode, struct file *f)
-{
- struct brcmf_debugfs_entry *entry = inode->i_private;
-
- return single_open(f, entry->read, entry->drvr->bus_if->dev);
-}
-
-static const struct file_operations brcmf_debugfs_def_ops = {
- .owner = THIS_MODULE,
- .open = brcmf_debugfs_entry_open,
- .release = single_release,
- .read = seq_read,
- .llseek = seq_lseek
-};
-
int brcmf_debugfs_add_entry(struct brcmf_pub *drvr, const char *fn,
int (*read_fn)(struct seq_file *seq, void *data))
{
- struct dentry *dentry = drvr->dbgfs_dir;
- struct brcmf_debugfs_entry *entry;
-
- if (IS_ERR_OR_NULL(dentry))
- return -ENOENT;
-
- entry = devm_kzalloc(drvr->bus_if->dev, sizeof(*entry), GFP_KERNEL);
- if (!entry)
- return -ENOMEM;
-
- entry->read = read_fn;
- entry->drvr = drvr;
-
- dentry = debugfs_create_file(fn, S_IRUGO, dentry, entry,
- &brcmf_debugfs_def_ops);
+ struct dentry *e;
- return PTR_ERR_OR_ZERO(dentry);
+ e = debugfs_create_devm_seqfile(drvr->bus_if->dev, fn,
+ drvr->dbgfs_dir, read_fn);
+ return PTR_ERR_OR_ZERO(e);
}