Skip to content

Commit

Permalink
rtlwifi: Convert COMP_XX entries into a proper debugging mask
Browse files Browse the repository at this point in the history
The debugging macros contain a parameter COMP_XX that could be used as a
mask; however, the code turns all these various bits on at the same time.
This change implements them as a proper mask, and adds module parameters
to set the mask at load time.

The current name "debug" for the debug level has been changed to
"debug_level" to better differentiate it from "debug_mask".

The debug routines have also been changed to interrogate the structure
that is loaded at entry time. As a result, the structure rtl_debug is no
longer needed, and all references to it are deleted.

Signed-off-by: Larry Finger <[email protected]>
Cc: Ping-Ke Shih <[email protected]>
Signed-off-by: Kalle Valo <[email protected]>
Signed-off-by: Christian Lamparter <[email protected]>
  • Loading branch information
lwfinger authored and chunkeey committed Mar 29, 2017
1 parent 6972d8f commit 8ca6c03
Show file tree
Hide file tree
Showing 16 changed files with 75 additions and 106 deletions.
6 changes: 3 additions & 3 deletions rtlwifi/base.c
Original file line number Diff line number Diff line change
Expand Up @@ -2010,7 +2010,7 @@ static ssize_t rtl_show_debug_level(struct device *d,
struct ieee80211_hw *hw = dev_get_drvdata(d);
struct rtl_priv *rtlpriv = rtl_priv(hw);

return sprintf(buf, "0x%08X\n", rtlpriv->dbg.global_debuglevel);
return sprintf(buf, "0x%08X\n", rtlpriv->cfg->mod_params->debug_level);
}

static ssize_t rtl_store_debug_level(struct device *d,
Expand All @@ -2027,10 +2027,10 @@ static ssize_t rtl_store_debug_level(struct device *d,
RT_TRACE(rtlpriv, COMP_ERR, DBG_DMESG,
"%s is not in hex or decimal form.\n", buf);
} else {
rtlpriv->dbg.global_debuglevel = val;
rtlpriv->cfg->mod_params->debug_level = val;
RT_TRACE(rtlpriv, COMP_ERR, DBG_DMESG,
"debuglevel:%x\n",
rtlpriv->dbg.global_debuglevel);
rtlpriv->cfg->mod_params->debug_level);
}

return strnlen(buf, count);
Expand Down
43 changes: 10 additions & 33 deletions rtlwifi/debug.c
Original file line number Diff line number Diff line change
Expand Up @@ -31,35 +31,12 @@
#include "base.h"
#include "debug.h"

void rtl_dbgp_flag_init(struct ieee80211_hw *hw)
{
struct rtl_priv *rtlpriv = rtl_priv(hw);
u8 i;

rtlpriv->dbg.global_debugcomponents =
COMP_ERR | COMP_FW | COMP_INIT | COMP_RECV | COMP_SEND |
COMP_MLME | COMP_SCAN | COMP_INTR | COMP_LED | COMP_SEC |
COMP_BEACON | COMP_RATE | COMP_RXDESC | COMP_DIG | COMP_TXAGC |
COMP_POWER | COMP_POWER_TRACKING | COMP_BB_POWERSAVING | COMP_SWAS |
COMP_RF | COMP_TURBO | COMP_RATR | COMP_CMD |
COMP_EFUSE | COMP_QOS | COMP_MAC80211 | COMP_REGD | COMP_CHAN |
COMP_EASY_CONCURRENT | COMP_EFUSE | COMP_QOS | COMP_MAC80211 |
COMP_REGD | COMP_CHAN | COMP_BT_COEXIST;


for (i = 0; i < DBGP_TYPE_MAX; i++)
rtlpriv->dbg.dbgp_type[i] = 0;

/*Init Debug flag enable condition */
}
EXPORT_SYMBOL_GPL(rtl_dbgp_flag_init);

#ifdef CONFIG_RTLWIFI_DEBUG
void _rtl_dbg_trace(struct rtl_priv *rtlpriv, int comp, int level,
const char *fmt, ...)
{
if (unlikely((comp & rtlpriv->dbg.global_debugcomponents) &&
(level <= rtlpriv->dbg.global_debuglevel))) {
if (unlikely((comp & rtlpriv->cfg->mod_params->debug_mask) &&
(level <= rtlpriv->cfg->mod_params->debug_level))) {
struct va_format vaf;
va_list args;

Expand All @@ -68,7 +45,7 @@ void _rtl_dbg_trace(struct rtl_priv *rtlpriv, int comp, int level,
vaf.fmt = fmt;
vaf.va = &args;

pr_debug(":<%lx> %pV", in_interrupt(), &vaf);
pr_info(":<%lx> %pV", in_interrupt(), &vaf);

va_end(args);
}
Expand All @@ -78,8 +55,8 @@ EXPORT_SYMBOL_GPL(_rtl_dbg_trace);
void _rtl_dbg_print(struct rtl_priv *rtlpriv, u64 comp, int level,
const char *fmt, ...)
{
if (unlikely((comp & rtlpriv->dbg.global_debugcomponents) &&
(level <= rtlpriv->dbg.global_debuglevel))) {
if (unlikely((comp & rtlpriv->cfg->mod_params->debug_mask) &&
(level <= rtlpriv->cfg->mod_params->debug_level))) {
struct va_format vaf;
va_list args;

Expand All @@ -88,7 +65,7 @@ void _rtl_dbg_print(struct rtl_priv *rtlpriv, u64 comp, int level,
vaf.fmt = fmt;
vaf.va = &args;

pr_debug("%pV", &vaf);
pr_info("%pV", &vaf);

va_end(args);
}
Expand All @@ -99,10 +76,10 @@ void _rtl_dbg_print_data(struct rtl_priv *rtlpriv, u64 comp, int level,
const char *titlestring,
const void *hexdata, int hexdatalen)
{
if (unlikely(((comp) & rtlpriv->dbg.global_debugcomponents) &&
((level) <= rtlpriv->dbg.global_debuglevel))) {
pr_debug("In process \"%s\" (pid %i): %s\n",
current->comm, current->pid, titlestring);
if (unlikely(((comp) & rtlpriv->cfg->mod_params->debug_mask) &&
((level) <= rtlpriv->cfg->mod_params->debug_level))) {
pr_info("In process \"%s\" (pid %i): %s\n",
current->comm, current->pid, titlestring);
print_hex_dump_bytes("", DUMP_PREFIX_NONE,
hexdata, hexdatalen);
}
Expand Down
2 changes: 0 additions & 2 deletions rtlwifi/debug.h
Original file line number Diff line number Diff line change
Expand Up @@ -234,6 +234,4 @@ static inline void rtl_unregister_debugfs(struct ieee80211_hw *hw)
{
}
#endif /* CONFIG_RTLWIFI_DEBUGFS */

void rtl_dbgp_flag_init(struct ieee80211_hw *hw);
#endif
10 changes: 0 additions & 10 deletions rtlwifi/pci.c
Original file line number Diff line number Diff line change
Expand Up @@ -2188,16 +2188,6 @@ int rtl_pci_probe(struct pci_dev *pdev,
rtlpriv->intf_ops = &rtl_pci_ops;
rtlpriv->glb_var = &rtl_global_var;

/*
*init dbgp flags before all
*other functions, because we will
*use it in other funtions like
*RT_TRACE/RT_PRINT/RTL_PRINT_DATA
*you can not use these macro
*before this
*/
rtl_dbgp_flag_init(hw);

/* MEM map */
err = pci_request_regions(pdev, KBUILD_MODNAME);
if (err) {
Expand Down
11 changes: 6 additions & 5 deletions rtlwifi/rtl8188ee/sw.c
Original file line number Diff line number Diff line change
Expand Up @@ -131,8 +131,6 @@ int rtl88e_init_sw_vars(struct ieee80211_hw *hw)
rtlpci->irq_mask[1] = (u32) (IMR_RXFOVW | 0);
rtlpci->sys_irq_mask = (u32) (HSIMR_PDN_INT_EN | HSIMR_RON_INT_EN);

/* for debug level */
rtlpriv->dbg.global_debuglevel = rtlpriv->cfg->mod_params->debug;
/* for LPS & IPS */
rtlpriv->psc.inactiveps = rtlpriv->cfg->mod_params->inactiveps;
rtlpriv->psc.swctrl_lps = rtlpriv->cfg->mod_params->swctrl_lps;
Expand Down Expand Up @@ -276,7 +274,8 @@ static struct rtl_mod_params rtl88ee_mod_params = {
.swctrl_lps = false,
.fwctrl_lps = false,
.msi_support = true,
.debug = 0,
.debug_level = 0,
.debug_mask = 0,
};

static const struct rtl_hal_cfg rtl88ee_hal_cfg = {
Expand Down Expand Up @@ -392,7 +391,8 @@ MODULE_DESCRIPTION("Realtek 8188E 802.11n PCI wireless");
MODULE_FIRMWARE("rtlwifi/rtl8188efw.bin");

module_param_named(swenc, rtl88ee_mod_params.sw_crypto, bool, 0444);
module_param_named(debug, rtl88ee_mod_params.debug, int, 0444);
module_param_named(debug_level, rtl88ee_mod_params.debug_level, int, 0644);
module_param_named(debug_mask, rtl88ee_mod_params.debug_mask, ullong, 0644);
module_param_named(ips, rtl88ee_mod_params.inactiveps, bool, 0444);
module_param_named(swlps, rtl88ee_mod_params.swctrl_lps, bool, 0444);
module_param_named(fwlps, rtl88ee_mod_params.fwctrl_lps, bool, 0444);
Expand All @@ -404,7 +404,8 @@ MODULE_PARM_DESC(ips, "Set to 0 to not use link power save (default 1)\n");
MODULE_PARM_DESC(swlps, "Set to 1 to use SW control power save (default 0)\n");
MODULE_PARM_DESC(fwlps, "Set to 1 to use FW control power save (default 1)\n");
MODULE_PARM_DESC(msi, "Set to 1 to use MSI interrupts mode (default 1)\n");
MODULE_PARM_DESC(debug, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(debug_level, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(debug_mask, "Set debug mask (default 0)");
MODULE_PARM_DESC(disable_watchdog, "Set to 1 to disable the watchdog (default 0)\n");

static SIMPLE_DEV_PM_OPS(rtlwifi_pm_ops, rtl_pci_suspend, rtl_pci_resume);
Expand Down
11 changes: 6 additions & 5 deletions rtlwifi/rtl8192ce/sw.c
Original file line number Diff line number Diff line change
Expand Up @@ -130,8 +130,6 @@ int rtl92c_init_sw_vars(struct ieee80211_hw *hw)

rtlpci->irq_mask[1] = (u32) (IMR_CPWM | IMR_C2HCMD | 0);

/* for debug level */
rtlpriv->dbg.global_debuglevel = rtlpriv->cfg->mod_params->debug;
/* for LPS & IPS */
rtlpriv->psc.inactiveps = rtlpriv->cfg->mod_params->inactiveps;
rtlpriv->psc.swctrl_lps = rtlpriv->cfg->mod_params->swctrl_lps;
Expand Down Expand Up @@ -247,7 +245,8 @@ static struct rtl_mod_params rtl92ce_mod_params = {
.inactiveps = true,
.swctrl_lps = false,
.fwctrl_lps = true,
.debug = 0,
.debug_level = 0,
.debug_mask = 0,
};

static const struct rtl_hal_cfg rtl92ce_hal_cfg = {
Expand Down Expand Up @@ -364,15 +363,17 @@ MODULE_FIRMWARE("rtlwifi/rtl8192cfwU.bin");
MODULE_FIRMWARE("rtlwifi/rtl8192cfwU_B.bin");

module_param_named(swenc, rtl92ce_mod_params.sw_crypto, bool, 0444);
module_param_named(debug, rtl92ce_mod_params.debug, int, 0444);
module_param_named(debug_level, rtl92ce_mod_params.debug_level, int, 0644);
module_param_named(debug_mask, rtl92ce_mod_params.debug_mask, ullong, 0644);
module_param_named(ips, rtl92ce_mod_params.inactiveps, bool, 0444);
module_param_named(swlps, rtl92ce_mod_params.swctrl_lps, bool, 0444);
module_param_named(fwlps, rtl92ce_mod_params.fwctrl_lps, bool, 0444);
MODULE_PARM_DESC(swenc, "Set to 1 for software crypto (default 0)\n");
MODULE_PARM_DESC(ips, "Set to 0 to not use link power save (default 1)\n");
MODULE_PARM_DESC(swlps, "Set to 1 to use SW control power save (default 0)\n");
MODULE_PARM_DESC(fwlps, "Set to 1 to use FW control power save (default 1)\n");
MODULE_PARM_DESC(debug, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(debug_level, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(debug_mask, "Set debug mask (default 0)");

static SIMPLE_DEV_PM_OPS(rtlwifi_pm_ops, rtl_pci_suspend, rtl_pci_resume);

Expand Down
10 changes: 6 additions & 4 deletions rtlwifi/rtl8192cu/sw.c
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,6 @@ static int rtl92cu_init_sw_vars(struct ieee80211_hw *hw)
rtlpriv->dm.dm_flag = 0;
rtlpriv->dm.disable_framebursting = false;
rtlpriv->dm.thermalvalue = 0;
rtlpriv->dbg.global_debuglevel = rtlpriv->cfg->mod_params->debug;
rtlpriv->cfg->mod_params->sw_crypto =
rtlpriv->cfg->mod_params->sw_crypto;

Expand Down Expand Up @@ -160,13 +159,16 @@ static struct rtl_hal_ops rtl8192cu_hal_ops = {

static struct rtl_mod_params rtl92cu_mod_params = {
.sw_crypto = 0,
.debug = 0,
.debug_level = 0,
.debug_mask = 0,
};

module_param_named(swenc, rtl92cu_mod_params.sw_crypto, bool, 0444);
module_param_named(debug, rtl92cu_mod_params.debug, int, 0444);
module_param_named(debug_level, rtl92cu_mod_params.debug_level, int, 0644);
module_param_named(debug_mask, rtl92cu_mod_params.debug_mask, ullong, 0644);
MODULE_PARM_DESC(swenc, "Set to 1 for software crypto (default 0)\n");
MODULE_PARM_DESC(debug, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(debug_level, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(debug_mask, "Set debug mask (default 0)");

static struct rtl_hal_usbint_cfg rtl92cu_interface_cfg = {
/* rx */
Expand Down
11 changes: 6 additions & 5 deletions rtlwifi/rtl8192de/sw.c
Original file line number Diff line number Diff line change
Expand Up @@ -140,8 +140,6 @@ static int rtl92d_init_sw_vars(struct ieee80211_hw *hw)

rtlpci->irq_mask[1] = (u32) (IMR_CPWM | IMR_C2HCMD);

/* for debug level */
rtlpriv->dbg.global_debuglevel = rtlpriv->cfg->mod_params->debug;
/* for LPS & IPS */
rtlpriv->psc.inactiveps = rtlpriv->cfg->mod_params->inactiveps;
rtlpriv->psc.swctrl_lps = rtlpriv->cfg->mod_params->swctrl_lps;
Expand Down Expand Up @@ -254,7 +252,8 @@ static struct rtl_mod_params rtl92de_mod_params = {
.inactiveps = true,
.swctrl_lps = true,
.fwctrl_lps = false,
.debug = 0,
.debug_level = 0,
.debug_mask = 0,
};

static const struct rtl_hal_cfg rtl92de_hal_cfg = {
Expand Down Expand Up @@ -364,15 +363,17 @@ MODULE_DESCRIPTION("Realtek 8192DE 802.11n Dual Mac PCI wireless");
MODULE_FIRMWARE("rtlwifi/rtl8192defw.bin");

module_param_named(swenc, rtl92de_mod_params.sw_crypto, bool, 0444);
module_param_named(debug, rtl92de_mod_params.debug, int, 0444);
module_param_named(debug_level, rtl92de_mod_params.debug_level, int, 0644);
module_param_named(ips, rtl92de_mod_params.inactiveps, bool, 0444);
module_param_named(swlps, rtl92de_mod_params.swctrl_lps, bool, 0444);
module_param_named(fwlps, rtl92de_mod_params.fwctrl_lps, bool, 0444);
module_param_named(debug_mask, rtl92de_mod_params.debug_mask, ullong, 0644);
MODULE_PARM_DESC(swenc, "Set to 1 for software crypto (default 0)\n");
MODULE_PARM_DESC(ips, "Set to 0 to not use link power save (default 1)\n");
MODULE_PARM_DESC(swlps, "Set to 1 to use SW control power save (default 1)\n");
MODULE_PARM_DESC(fwlps, "Set to 1 to use FW control power save (default 0)\n");
MODULE_PARM_DESC(debug, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(debug_level, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(debug_mask, "Set debug mask (default 0)");

static SIMPLE_DEV_PM_OPS(rtlwifi_pm_ops, rtl_pci_suspend, rtl_pci_resume);

Expand Down
11 changes: 6 additions & 5 deletions rtlwifi/rtl8192ee/sw.c
Original file line number Diff line number Diff line change
Expand Up @@ -133,8 +133,6 @@ int rtl92ee_init_sw_vars(struct ieee80211_hw *hw)
0);
rtlpci->irq_mask[1] = (u32)(IMR_RXFOVW | 0);

/* for debug level */
rtlpriv->dbg.global_debuglevel = rtlpriv->cfg->mod_params->debug;
/* for LPS & IPS */
rtlpriv->psc.inactiveps = rtlpriv->cfg->mod_params->inactiveps;
rtlpriv->psc.swctrl_lps = rtlpriv->cfg->mod_params->swctrl_lps;
Expand Down Expand Up @@ -258,7 +256,8 @@ static struct rtl_mod_params rtl92ee_mod_params = {
.swctrl_lps = false,
.fwctrl_lps = true,
.msi_support = true,
.debug = 0,
.debug_level = 0,
.debug_mask = 0,
};

static const struct rtl_hal_cfg rtl92ee_hal_cfg = {
Expand Down Expand Up @@ -368,7 +367,8 @@ MODULE_DESCRIPTION("Realtek 8192EE 802.11n PCI wireless");
MODULE_FIRMWARE("rtlwifi/rtl8192eefw.bin");

module_param_named(swenc, rtl92ee_mod_params.sw_crypto, bool, 0444);
module_param_named(debug, rtl92ee_mod_params.debug, int, 0444);
module_param_named(debug_level, rtl92ee_mod_params.debug_level, int, 0644);
module_param_named(debug_mask, rtl92ee_mod_params.debug_mask, ullong, 0644);
module_param_named(ips, rtl92ee_mod_params.inactiveps, bool, 0444);
module_param_named(swlps, rtl92ee_mod_params.swctrl_lps, bool, 0444);
module_param_named(fwlps, rtl92ee_mod_params.fwctrl_lps, bool, 0444);
Expand All @@ -380,7 +380,8 @@ MODULE_PARM_DESC(ips, "Set to 0 to not use link power save (default 1)\n");
MODULE_PARM_DESC(swlps, "Set to 1 to use SW control power save (default 0)\n");
MODULE_PARM_DESC(fwlps, "Set to 1 to use FW control power save (default 1)\n");
MODULE_PARM_DESC(msi, "Set to 1 to use MSI interrupts mode (default 1)\n");
MODULE_PARM_DESC(debug, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(debug_level, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(debug_mask, "Set debug mask (default 0)");
MODULE_PARM_DESC(disable_watchdog, "Set to 1 to disable the watchdog (default 0)\n");

static SIMPLE_DEV_PM_OPS(rtlwifi_pm_ops, rtl_pci_suspend, rtl_pci_resume);
Expand Down
11 changes: 6 additions & 5 deletions rtlwifi/rtl8192se/sw.c
Original file line number Diff line number Diff line change
Expand Up @@ -153,8 +153,6 @@ static int rtl92s_init_sw_vars(struct ieee80211_hw *hw)

rtlpci->first_init = true;

/* for debug level */
rtlpriv->dbg.global_debuglevel = rtlpriv->cfg->mod_params->debug;
/* for LPS & IPS */
rtlpriv->psc.inactiveps = rtlpriv->cfg->mod_params->inactiveps;
rtlpriv->psc.swctrl_lps = rtlpriv->cfg->mod_params->swctrl_lps;
Expand Down Expand Up @@ -273,7 +271,8 @@ static struct rtl_mod_params rtl92se_mod_params = {
.inactiveps = true,
.swctrl_lps = true,
.fwctrl_lps = false,
.debug = 0,
.debug_level = 0,
.debug_mask = 0,
};

/* Because memory R/W bursting will cause system hang/crash
Expand Down Expand Up @@ -392,15 +391,17 @@ MODULE_DESCRIPTION("Realtek 8192S/8191S 802.11n PCI wireless");
MODULE_FIRMWARE(RTL8192SE_FW_NAME);

module_param_named(swenc, rtl92se_mod_params.sw_crypto, bool, 0444);
module_param_named(debug, rtl92se_mod_params.debug, int, 0444);
module_param_named(debug_level, rtl92se_mod_params.debug_level, int, 0644);
module_param_named(debug_mask, rtl92se_mod_params.debug_mask, ullong, 0644);
module_param_named(ips, rtl92se_mod_params.inactiveps, bool, 0444);
module_param_named(swlps, rtl92se_mod_params.swctrl_lps, bool, 0444);
module_param_named(fwlps, rtl92se_mod_params.fwctrl_lps, bool, 0444);
MODULE_PARM_DESC(swenc, "Set to 1 for software crypto (default 0)\n");
MODULE_PARM_DESC(ips, "Set to 0 to not use link power save (default 1)\n");
MODULE_PARM_DESC(swlps, "Set to 1 to use SW control power save (default 1)\n");
MODULE_PARM_DESC(fwlps, "Set to 1 to use FW control power save (default 0)\n");
MODULE_PARM_DESC(debug, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(debug_level, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(debug_mask, "Set debug mask (default 0)");

static SIMPLE_DEV_PM_OPS(rtlwifi_pm_ops, rtl_pci_suspend, rtl_pci_resume);

Expand Down
9 changes: 5 additions & 4 deletions rtlwifi/rtl8192su/sw.c
Original file line number Diff line number Diff line change
Expand Up @@ -63,8 +63,6 @@ static int rtl92su_init_sw_vars(struct ieee80211_hw *hw)
rtlpriv->rtlhal.bandset = BAND_ON_2_4G;
rtlpriv->rtlhal.macphymode = SINGLEMAC_SINGLEPHY;

/* for debug level */
rtlpriv->dbg.global_debuglevel = rtlpriv->cfg->mod_params->debug;
/* for LPS & IPS */
rtlpriv->psc.inactiveps = rtlpriv->cfg->mod_params->inactiveps;
rtlpriv->psc.swctrl_lps = rtlpriv->cfg->mod_params->swctrl_lps;
Expand Down Expand Up @@ -168,7 +166,8 @@ static struct rtl_mod_params rtl92su_mod_params = {
.inactiveps = false,
.fwctrl_lps = false,
.swctrl_lps = false,
.debug = DBG_EMERG,
.debug_level = 0,
.debug_mask = 0,
};

static struct rtl_hal_usbint_cfg rtl92su_interface_cfg = {
Expand Down Expand Up @@ -428,7 +427,9 @@ MODULE_DESCRIPTION("Realtek 8188S/8191S/8192S 802.11n USB wireless");
MODULE_FIRMWARE(RTL8192SU_FW_NAME);

module_param_named(swenc, rtl92su_mod_params.sw_crypto, bool, 0444);
module_param_named(debug, rtl92su_mod_params.debug, int, 0444);
module_param_named(debug_level, rtl92su_mod_params.debug_level, int, 0644);
module_param_named(debug_mask, rtl92su_mod_params.debug_mask, ullong, 0644);

MODULE_PARM_DESC(swenc, "Set to 0 for hardware crypto (default 1)\n");
MODULE_PARM_DESC(debug, "Set debug level (0-5) (default 0)");
MODULE_PARM_DESC(swlps, "Set to 1 to use SW control power save (default 0)\n");
Expand Down
Loading

0 comments on commit 8ca6c03

Please sign in to comment.