]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - contrib/llvm/tools/lldb/tools/lldb-mi/MICmdMgr.cpp
Merge ^/head r288836 through r288925.
[FreeBSD/FreeBSD.git] / contrib / llvm / tools / lldb / tools / lldb-mi / MICmdMgr.cpp
1 //===-- MICmdMgr.cpp --------------------------------------------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9
10 // In-house headers:
11 #include "MICmdMgr.h"
12 #include "MICmnResources.h"
13 #include "MICmnLog.h"
14 #include "MICmdInterpreter.h"
15 #include "MICmdFactory.h"
16 #include "MICmdInvoker.h"
17 #include "MICmdBase.h"
18 #include "MIUtilSingletonBase.h"
19 #include "MIUtilSingletonHelper.h"
20
21 //++ ------------------------------------------------------------------------------------
22 // Details: CMICmdMgr constructor.
23 // Type:    Method.
24 // Args:    None.
25 // Return:  None.
26 // Throws:  None.
27 //--
28 CMICmdMgr::CMICmdMgr(void)
29     : m_interpretor(CMICmdInterpreter::Instance())
30     , m_factory(CMICmdFactory::Instance())
31     , m_invoker(CMICmdInvoker::Instance())
32 {
33 }
34
35 //++ ------------------------------------------------------------------------------------
36 // Details: CMICmdMgr destructor.
37 // Type:    Overridable.
38 // Args:    None.
39 // Return:  None.
40 // Throws:  None.
41 //--
42 CMICmdMgr::~CMICmdMgr(void)
43 {
44     Shutdown();
45 }
46
47 //++ ------------------------------------------------------------------------------------
48 // Details: Initialize resources for *this Command Manager.
49 // Type:    Method.
50 // Args:    None.
51 // Return:  MIstatus::success - Functionality succeeded.
52 //          MIstatus::failure - Functionality failed.
53 // Throws:  None.
54 //--
55 bool
56 CMICmdMgr::Initialize(void)
57 {
58     m_clientUsageRefCnt++;
59
60     if (m_bInitialized)
61         return MIstatus::success;
62
63     bool bOk = MIstatus::success;
64     CMIUtilString errMsg;
65
66     // Note initialization order is important here as some resources depend on previous
67     MI::ModuleInit<CMICmnLog>(IDS_MI_INIT_ERR_LOG, bOk, errMsg);
68     MI::ModuleInit<CMICmnResources>(IDS_MI_INIT_ERR_RESOURCES, bOk, errMsg);
69     if (bOk && !m_interpretor.Initialize())
70     {
71         bOk = false;
72         errMsg = CMIUtilString::Format(MIRSRC(IDS_MI_INIT_ERR_CMDINTERPRETER), m_interpretor.GetErrorDescription().c_str());
73     }
74     if (bOk && !m_factory.Initialize())
75     {
76         bOk = false;
77         errMsg = CMIUtilString::Format(MIRSRC(IDS_MI_INIT_ERR_CMDFACTORY), m_factory.GetErrorDescription().c_str());
78     }
79     if (bOk && !m_invoker.Initialize())
80     {
81         bOk = false;
82         errMsg = CMIUtilString::Format(MIRSRC(IDS_MI_INIT_ERR_CMDINVOKER), m_invoker.GetErrorDescription().c_str());
83     }
84     m_bInitialized = bOk;
85
86     if (!bOk)
87     {
88         CMIUtilString strInitError(CMIUtilString::Format(MIRSRC(IDS_MI_INIT_ERR_CMDMGR), errMsg.c_str()));
89         SetErrorDescription(strInitError);
90         return MIstatus::failure;
91     }
92
93     return MIstatus::success;
94 }
95
96 //++ ------------------------------------------------------------------------------------
97 // Details: Release resources for *this Command Manager.
98 // Type:    Method.
99 // Args:    None.
100 // Return:  MIstatus::success - Functionality succeeded.
101 //          MIstatus::failure - Functionality failed.
102 // Throws:  None.
103 //--
104 bool
105 CMICmdMgr::Shutdown(void)
106 {
107     if (--m_clientUsageRefCnt > 0)
108         return MIstatus::success;
109
110     if (!m_bInitialized)
111         return MIstatus::success;
112
113     m_bInitialized = false;
114
115     ClrErrorDescription();
116
117     bool bOk = MIstatus::success;
118     CMIUtilString errMsg;
119
120     // Tidy up
121     m_setCmdDeleteCallback.clear();
122
123     // Note shutdown order is important here
124     if (!m_invoker.Shutdown())
125     {
126         bOk = false;
127         errMsg += CMIUtilString::Format(MIRSRC(IDS_MI_SHTDWN_ERR_CMDINVOKER), m_invoker.GetErrorDescription().c_str());
128     }
129     if (!m_factory.Shutdown())
130     {
131         bOk = false;
132         if (!errMsg.empty())
133             errMsg += ", ";
134         errMsg += CMIUtilString::Format(MIRSRC(IDS_MI_SHTDWN_ERR_CMDFACTORY), m_factory.GetErrorDescription().c_str());
135     }
136     if (!m_interpretor.Shutdown())
137     {
138         bOk = false;
139         if (!errMsg.empty())
140             errMsg += ", ";
141         errMsg += CMIUtilString::Format(MIRSRC(IDS_MI_SHTDWN_ERR_CMDINTERPRETER), m_interpretor.GetErrorDescription().c_str());
142     }
143     MI::ModuleShutdown<CMICmnResources>(IDS_MI_INIT_ERR_RESOURCES, bOk, errMsg);
144     MI::ModuleShutdown<CMICmnLog>(IDS_MI_INIT_ERR_LOG, bOk, errMsg);
145
146     if (!bOk)
147     {
148         SetErrorDescriptionn(MIRSRC(IDS_MI_SHUTDOWN_ERR), errMsg.c_str());
149     }
150
151     return MIstatus::success;
152 }
153
154 //++ ------------------------------------------------------------------------------------
155 // Details: Establish whether the text data is an MI format type command.
156 // Type:    Method.
157 // Args:    vTextLine               - (R) Text data to interpret.
158 //          vwbYesValid             - (W) True = MI type command, false = not recognised.
159 //          vwbCmdNotInCmdFactor    - (W) True = MI command not found in the command factor, false = recognised.
160 // Return:  MIstatus::success - Functionality succeeded.
161 //          MIstatus::failure - Functionality failed.
162 // Throws:  None.
163 //--
164 bool
165 CMICmdMgr::CmdInterpret(const CMIUtilString &vTextLine, bool &vwbYesValid, bool &vwbCmdNotInCmdFactor, SMICmdData &rwCmdData)
166 {
167     return m_interpretor.ValidateIsMi(vTextLine, vwbYesValid, vwbCmdNotInCmdFactor, rwCmdData);
168 }
169
170 //++ ------------------------------------------------------------------------------------
171 // Details: Having previously had the potential command validated and found valid now
172 //          get the command executed.
173 //          If the Functionality returns MIstatus::failure call GetErrorDescription().
174 //          This function is used by the application's main thread.
175 // Type:    Method.
176 // Args:    vCmdData    - (RW) Command meta data.
177 // Return:  MIstatus::success - Functionality succeeded.
178 //          MIstatus::failure - Functionality failed.
179 // Throws:  None.
180 //--
181 bool
182 CMICmdMgr::CmdExecute(const SMICmdData &vCmdData)
183 {
184     bool bOk = MIstatus::success;
185
186     // Pass the command's meta data structure to the command
187     // so it can update it if required. (Need to copy it out of the
188     // command before the command is deleted)
189     CMICmdBase *pCmd = nullptr;
190     bOk = m_factory.CmdCreate(vCmdData.strMiCmd, vCmdData, pCmd);
191     if (!bOk)
192     {
193         const CMIUtilString errMsg(
194             CMIUtilString::Format(MIRSRC(IDS_CMDMGR_ERR_CMD_FAILED_CREATE), m_factory.GetErrorDescription().c_str()));
195         SetErrorDescription(errMsg);
196         return MIstatus::failure;
197     }
198
199     bOk = m_invoker.CmdExecute(*pCmd);
200     if (!bOk)
201     {
202         const CMIUtilString errMsg(CMIUtilString::Format(MIRSRC(IDS_CMDMGR_ERR_CMD_INVOKER), m_invoker.GetErrorDescription().c_str()));
203         SetErrorDescription(errMsg);
204         return MIstatus::failure;
205     }
206
207     return bOk;
208 }
209
210 //++ ------------------------------------------------------------------------------------
211 // Details: Iterate all interested clients and tell them a command is being deleted.
212 // Type:    Method.
213 // Args:    vCmdData    - (RW) The command to be deleted.
214 // Return:  MIstatus::success - Functional succeeded.
215 //          MIstatus::failure - Functional failed.
216 // Throws:  None.
217 //--
218 bool
219 CMICmdMgr::CmdDelete(SMICmdData vCmdData)
220 {
221     // Note vCmdData is a copy! The command holding its copy will be deleted soon
222     // we still need to iterate callback clients after a command object is deleted
223
224     m_setCmdDeleteCallback.Delete(vCmdData);
225
226     return MIstatus::success;
227 }
228
229 //++ ------------------------------------------------------------------------------------
230 // Details: Register an object to be called when a command object is deleted.
231 // Type:    Method.
232 // Args:    vObject - (R) A new interested client.
233 // Return:  MIstatus::success - Functional succeeded.
234 //          MIstatus::failure - Functional failed.
235 // Throws:  None.
236 //--
237 bool
238 CMICmdMgr::CmdRegisterForDeleteNotification(CMICmdMgrSetCmdDeleteCallback::ICallback &vObject)
239 {
240     return m_setCmdDeleteCallback.Register(vObject);
241 }
242
243 //++ ------------------------------------------------------------------------------------
244 // Details: Unregister an object from being called when a command object is deleted.
245 // Type:    Method.
246 // Args:    vObject - (R) The was interested client.
247 // Return:  MIstatus::success - Functional succeeded.
248 //          MIstatus::failure - Functional failed.
249 // Throws:  None.
250 //--
251 bool
252 CMICmdMgr::CmdUnregisterForDeleteNotification(CMICmdMgrSetCmdDeleteCallback::ICallback &vObject)
253 {
254     return m_setCmdDeleteCallback.Unregister(vObject);
255 }