1 /*
2  * Copyright (C) 2004-2020 ZNC, see the NOTICE file for details.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *     http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #include <znc/FileUtils.h>
18 #include <znc/Server.h>
19 #include <znc/IRCNetwork.h>
20 #include <znc/User.h>
21 #include <znc/ZNCDebug.h>
22 
23 class CAdminDebugMod : public CModule {
24   private:
25       CString m_sEnabledBy;
26 
27   public:
MODCONSTRUCTOR(CAdminDebugMod)28     MODCONSTRUCTOR(CAdminDebugMod) {
29         AddHelpCommand();
30         AddCommand("Enable", "", t_d("Enable Debug Mode"),
31                    [=](const CString& sLine) { CommandEnable(sLine); });
32         AddCommand("Disable", "", t_d("Disable Debug Mode"),
33                    [=](const CString& sLine) { CommandDisable(sLine); });
34         AddCommand("Status", "", t_d("Show the Debug Mode status"),
35                    [=](const CString& sLine) { CommandStatus(sLine); });
36     }
37 
CommandEnable(const CString & sCommand)38     void CommandEnable(const CString& sCommand) {
39         if (!GetUser()->IsAdmin()) {
40             PutModule(t_s("Access denied!"));
41             return;
42         }
43 
44         ToggleDebug(true, GetUser()->GetNick());
45     }
46 
CommandDisable(const CString & sCommand)47     void CommandDisable(const CString& sCommand) {
48         if (!GetUser()->IsAdmin()) {
49             PutModule(t_s("Access denied!"));
50             return;
51         }
52 
53         ToggleDebug(false, m_sEnabledBy);
54     }
55 
ToggleDebug(bool bEnable,const CString & sEnabledBy)56     bool ToggleDebug(bool bEnable, const CString& sEnabledBy) {
57         if (!CDebug::StdoutIsTTY()) {
58             PutModule(t_s("Failure. We need to be running with a TTY. (is ZNC running with --foreground?)"));
59             return false;
60         }
61 
62         bool bValue = CDebug::Debug();
63 
64         if (bEnable == bValue) {
65             if (bEnable) {
66                 PutModule(t_s("Already enabled."));
67             } else {
68                 PutModule(t_s("Already disabled."));
69             }
70             return false;
71         }
72 
73         CDebug::SetDebug(bEnable);
74         CString sEnabled = bEnable ? "on" : "off";
75         CZNC::Get().Broadcast(
76             "An administrator has just turned Debug Mode \02" + sEnabled +
77             "\02. It was enabled by \02" + sEnabledBy + "\02.");
78         if (bEnable) {
79             CZNC::Get().Broadcast(
80                 "Messages, credentials, and other sensitive data may become "
81                 "exposed to the host during this period.");
82             m_sEnabledBy = sEnabledBy;
83         } else {
84             m_sEnabledBy = "";
85         }
86 
87         return true;
88     }
89 
CommandStatus(const CString & sCommand)90     void CommandStatus(const CString& sCommand) {
91         if (CDebug::Debug()) {
92             PutModule(t_s("Debugging mode is \02on\02."));
93         } else {
94              PutModule(t_s("Debugging mode is \02off\02."));
95         }
96         PutModule(t_s("Logging to: \02stdout\02."));
97     }
98 };
99 
100 template <>
TModInfo(CModInfo & Info)101 void TModInfo<CAdminDebugMod>(CModInfo& Info) {
102     Info.SetWikiPage("admindebug");
103 }
104 
105 GLOBALMODULEDEFS(CAdminDebugMod, t_s("Enable Debug mode dynamically."))
106