• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2023 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 #include "ability_command.h"
16 
17 #include <csignal>
18 #include <cstdlib>
19 #include <getopt.h>
20 #include <regex>
21 #include "ability_manager_client.h"
22 #include "app_mgr_client.h"
23 #include "hilog_wrapper.h"
24 #include "iservice_registry.h"
25 #include "mission_snapshot.h"
26 #include "bool_wrapper.h"
27 #include "sa_mgr_client.h"
28 #include "system_ability_definition.h"
29 #include "test_observer.h"
30 
31 using namespace OHOS::AppExecFwk;
32 
33 namespace OHOS {
34 namespace AAFwk {
35 namespace {
36 constexpr size_t PARAM_LENGTH = 1024;
37 constexpr int EXTRA_ARGUMENTS_FOR_KEY_VALUE_PAIR = 1;
38 constexpr int EXTRA_ARGUMENTS_FOR_NULL_STRING = 0;
39 constexpr int OPTION_PARAMETER_VALUE_OFFSET = 1;
40 
41 constexpr int OPTION_PARAMETER_INTEGER = 257;
42 constexpr int OPTION_PARAMETER_STRING = 258;
43 constexpr int OPTION_PARAMETER_BOOL = 259;
44 constexpr int OPTION_PARAMETER_NULL_STRING = 260;
45 
46 const std::string SHORT_OPTIONS = "ch:d:a:b:e:t:p:s:m:A:U:CDSN";
47 constexpr struct option LONG_OPTIONS[] = {
48     {"help", no_argument, nullptr, 'h'},
49     {"device", required_argument, nullptr, 'd'},
50     {"ability", required_argument, nullptr, 'a'},
51     {"bundle", required_argument, nullptr, 'b'},
52     {"perf", required_argument, nullptr, 'p'},
53     {"setting", required_argument, nullptr, 's'},
54     {"module", required_argument, nullptr, 'm'},
55     {"cold-start", no_argument, nullptr, 'C'},
56     {"debug", no_argument, nullptr, 'D'},
57     {"native-debug", no_argument, nullptr, 'N'},
58     {"action", required_argument, nullptr, 'A'},
59     {"URI", required_argument, nullptr, 'U'},
60     {"entity", required_argument, nullptr, 'e'},
61     {"type", required_argument, nullptr, 't'},
62     {"pi", required_argument, nullptr, OPTION_PARAMETER_INTEGER},
63     {"ps", required_argument, nullptr, OPTION_PARAMETER_STRING},
64     {"pb", required_argument, nullptr, OPTION_PARAMETER_BOOL},
65     {"psn", required_argument, nullptr, OPTION_PARAMETER_NULL_STRING},
66     {nullptr, 0, nullptr, 0},
67 };
68 const std::string SHORT_OPTIONS_APPLICATION_NOT_RESPONDING = "hp:";
69 #ifdef ABILITY_COMMAND_FOR_TEST
70 constexpr struct option LONG_OPTIONS_ApplicationNotResponding[] = {
71     {"help", no_argument, nullptr, 'h'},
72     {"pid", required_argument, nullptr, 'p'},
73     {nullptr, 0, nullptr, 0},
74 };
75 #endif
76 #ifdef ABILITY_FAULT_AND_EXIT_TEST
77 const std::string SHORT_OPTIONS_FORCE_EXIT_APP = "hp:r:";
78 constexpr struct option LONG_OPTIONS_FORCE_EXIT_APP[] = {
79     { "help", no_argument, nullptr, 'h' },
80     { "pid", required_argument, nullptr, 'p' },
81     { "reason", required_argument, nullptr, 'r' },
82     { nullptr, 0, nullptr, 0 },
83 };
84 const std::string SHORT_OPTIONS_NOTIFY_APP_FAULT = "hn:m:s:t:p:";
85 constexpr struct option LONG_OPTIONS_NOTIFY_APP_FAULT[] = {
86     {"help", no_argument, nullptr, 'h'},
87     {"errorName", required_argument, nullptr, 'n'},
88     {"errorMessage", required_argument, nullptr, 'm'},
89     {"errorStack", required_argument, nullptr, 's'},
90     {"faultType", required_argument, nullptr, 't'},
91     {"pid", required_argument, nullptr, 'p'},
92     {nullptr, 0, nullptr, 0},
93 };
94 #endif
95 const std::string SHORT_OPTIONS_DUMPSYS = "hal::i:e::p::r::d::u:c";
96 constexpr struct option LONG_OPTIONS_DUMPSYS[] = {
97     {"help", no_argument, nullptr, 'h'},
98     {"all", no_argument, nullptr, 'a'},
99     {"mission-list", no_argument, nullptr, 'l'},
100     {"ability", required_argument, nullptr, 'i'},
101     {"extension", no_argument, nullptr, 'e'},
102     {"pending", no_argument, nullptr, 'p'},
103     {"process", no_argument, nullptr, 'r'},
104     {"data", no_argument, nullptr, 'd'},
105     {"userId", required_argument, nullptr, 'u'},
106     {"client", no_argument, nullptr, 'c'},
107     {nullptr, 0, nullptr, 0},
108 };
109 const std::string SHORT_OPTIONS_PROCESS = "ha:b:p:m:D:S";
110 constexpr struct option LONG_OPTIONS_PROCESS[] = {
111     {"help", no_argument, nullptr, 'h'},
112     {"ability", required_argument, nullptr, 'a'},
113     {"bundle", required_argument, nullptr, 'b'},
114     {"perf", required_argument, nullptr, 'p'},
115     {"module", required_argument, nullptr, 'm'},
116     {"debug", required_argument, nullptr, 'D'},
117     {nullptr, 0, nullptr, 0},
118 };
119 const std::string SHORT_OPTIONS_ATTACH = "hb:";
120 constexpr struct option LONG_OPTIONS_ATTACH[] = {
121     {"help", no_argument, nullptr, 'h'},
122     {"bundle", required_argument, nullptr, 'b'},
123     {nullptr, 0, nullptr, 0},
124 };
125 }  // namespace
126 
AbilityManagerShellCommand(int argc,char * argv[])127 AbilityManagerShellCommand::AbilityManagerShellCommand(int argc, char* argv[]) : ShellCommand(argc, argv, TOOL_NAME)
128 {
129     for (int i = 0; i < argc_; i++) {
130         HILOG_INFO("argv_[%{public}d]: %{public}s", i, argv_[i]);
131     }
132 }
133 
CreateCommandMap()134 ErrCode AbilityManagerShellCommand::CreateCommandMap()
135 {
136     commandMap_ = {
137         {"help", std::bind(&AbilityManagerShellCommand::RunAsHelpCommand, this)},
138         {"screen", std::bind(&AbilityManagerShellCommand::RunAsScreenCommand, this)},
139         {"start", std::bind(&AbilityManagerShellCommand::RunAsStartAbility, this)},
140         {"stop-service", std::bind(&AbilityManagerShellCommand::RunAsStopService, this)},
141         {"dump", std::bind(&AbilityManagerShellCommand::RunAsDumpsysCommand, this)},
142         {"force-stop", std::bind(&AbilityManagerShellCommand::RunAsForceStop, this)},
143         {"test", std::bind(&AbilityManagerShellCommand::RunAsTestCommand, this)},
144         {"process", std::bind(&AbilityManagerShellCommand::RunAsProcessCommand, this)},
145         {"attach", std::bind(&AbilityManagerShellCommand::RunAsAttachDebugCommand, this)},
146         {"detach", std::bind(&AbilityManagerShellCommand::RunAsDetachDebugCommand, this)},
147 #ifdef ABILITY_COMMAND_FOR_TEST
148         {"force-timeout", std::bind(&AbilityManagerShellCommand::RunForceTimeoutForTest, this)},
149         {"ApplicationNotResponding", std::bind(&AbilityManagerShellCommand::RunAsSendAppNotRespondingProcessID, this)},
150         {"block-ability", std::bind(&AbilityManagerShellCommand::RunAsBlockAbilityCommand, this)},
151         {"block-ams-service", std::bind(&AbilityManagerShellCommand::RunAsBlockAmsServiceCommand, this)},
152         {"block-app-service", std::bind(&AbilityManagerShellCommand::RunAsBlockAppServiceCommand, this)},
153 #endif
154 #ifdef ABILITY_FAULT_AND_EXIT_TEST
155         {"forceexitapp", std::bind(&AbilityManagerShellCommand::RunAsForceExitAppCommand, this)},
156         {"notifyappfault", std::bind(&AbilityManagerShellCommand::RunAsNotifyAppFaultCommand, this)},
157 #endif
158     };
159 
160     return OHOS::ERR_OK;
161 }
162 
CreateMessageMap()163 ErrCode AbilityManagerShellCommand::CreateMessageMap()
164 {
165     messageMap_ = {
166         //  code + message
167         {
168             RESOLVE_ABILITY_ERR,
169             "error: resolve ability err.",
170         },
171         {
172             GET_ABILITY_SERVICE_FAILED,
173             "error: get ability service failed.",
174         },
175         {
176             ABILITY_SERVICE_NOT_CONNECTED,
177             "error: ability service not connected.",
178         },
179         {
180             RESOLVE_APP_ERR,
181             "error: resolve app err.",
182         },
183         {
184             ABILITY_EXISTED,
185             "error: ability existed.",
186         },
187         {
188             CREATE_MISSION_STACK_FAILED,
189             "error: create mission stack failed.",
190         },
191         {
192             CREATE_ABILITY_RECORD_FAILED,
193             "error: create ability record failed.",
194         },
195         {
196             START_ABILITY_WAITING,
197             "start ability successfully. waiting...",
198         },
199         {
200             TERMINATE_LAUNCHER_DENIED,
201             "error: terminate launcher denied.",
202         },
203         {
204             CONNECTION_NOT_EXIST,
205             "error: connection not exist.",
206         },
207         {
208             INVALID_CONNECTION_STATE,
209             "error: invalid connection state.",
210         },
211         {
212             LOAD_ABILITY_TIMEOUT,
213             "error: load ability timeout.",
214         },
215         {
216             CONNECTION_TIMEOUT,
217             "error: connection timeout.",
218         },
219         {
220             GET_BUNDLE_MANAGER_SERVICE_FAILED,
221             "error: get bundle manager service failed.",
222         },
223         {
224             REMOVE_MISSION_FAILED,
225             "error: remove mission failed.",
226         },
227         {
228             INNER_ERR,
229             "error: inner err.",
230         },
231         {
232             GET_RECENT_MISSIONS_FAILED,
233             "error: get recent missions failed.",
234         },
235         {
236             REMOVE_STACK_LAUNCHER_DENIED,
237             "error: remove stack launcher denied.",
238         },
239         {
240             TARGET_ABILITY_NOT_SERVICE,
241             "error: target ability not service.",
242         },
243         {
244             TERMINATE_SERVICE_IS_CONNECTED,
245             "error: terminate service is connected.",
246         },
247         {
248             START_SERVICE_ABILITY_ACTIVATING,
249             "error: start service ability activating.",
250         },
251         {
252             KILL_PROCESS_FAILED,
253             "error: kill process failed.",
254         },
255         {
256             UNINSTALL_APP_FAILED,
257             "error: uninstall app failed.",
258         },
259         {
260             TERMINATE_ABILITY_RESULT_FAILED,
261             "error: terminate ability result failed.",
262         },
263         {
264             CHECK_PERMISSION_FAILED,
265             "error: check permission failed.",
266         },
267         {
268             NO_FOUND_ABILITY_BY_CALLER,
269             "error: no found ability by caller.",
270         },
271         {
272             ABILITY_VISIBLE_FALSE_DENY_REQUEST,
273             "error: ability visible false deny request.",
274         },
275         {
276             GET_BUNDLE_INFO_FAILED,
277             "error: get bundle info failed.",
278         },
279         {
280             KILL_PROCESS_KEEP_ALIVE,
281             "error: keep alive process can not be killed.",
282         },
283     };
284 
285     return OHOS::ERR_OK;
286 }
287 
init()288 ErrCode AbilityManagerShellCommand::init()
289 {
290     return AbilityManagerClient::GetInstance()->Connect();
291 }
292 
RunAsHelpCommand()293 ErrCode AbilityManagerShellCommand::RunAsHelpCommand()
294 {
295     resultReceiver_.append(HELP_MSG);
296 
297     return OHOS::ERR_OK;
298 }
299 
RunAsScreenCommand()300 ErrCode AbilityManagerShellCommand::RunAsScreenCommand()
301 {
302     HILOG_INFO("enter");
303 
304     int result = OHOS::ERR_OK;
305 
306     int option = -1;
307     int counter = 0;
308 
309     while (true) {
310         counter++;
311 
312         option = getopt_long(argc_, argv_, SHORT_OPTIONS.c_str(), LONG_OPTIONS, nullptr);
313 
314         HILOG_INFO("option: %{public}d, optopt: %{public}d, optind: %{public}d", option, optopt, optind);
315 
316         if (optind < 0 || optind > argc_) {
317             return OHOS::ERR_INVALID_VALUE;
318         }
319 
320         if (option == -1) {
321             // When scanning the first argument
322             if (counter == 1 && strcmp(argv_[optind], cmd_.c_str()) == 0) {
323                 // 'aa screen' with no option: aa screen
324                 // 'aa screen' with a wrong argument: aa screen xxx
325                 HILOG_INFO("'aa %{public}s' %{public}s.", HELP_MSG_NO_OPTION.c_str(), cmd_.c_str());
326                 resultReceiver_.append(HELP_MSG_NO_OPTION + "\n");
327                 result = OHOS::ERR_INVALID_VALUE;
328             }
329             break;
330         }
331 
332         if (option == '?') {
333             switch (optopt) {
334                 case 'p': {
335                     // 'aa screen -p' with no argument
336                     HILOG_INFO("'aa %{public}s -p' with no argument.", cmd_.c_str());
337 
338                     resultReceiver_.append("error: option ");
339                     resultReceiver_.append("requires a value.\n");
340 
341                     result = OHOS::ERR_INVALID_VALUE;
342                     break;
343                 }
344                 case 0: {
345                     // 'aa screen' with an unknown option: aa screen --x
346                     // 'aa screen' with an unknown option: aa screen --xxx
347                     std::string unknownOption = "";
348                     std::string unknownOptionMsg = GetUnknownOptionMsg(unknownOption);
349 
350                     HILOG_INFO("'aa screen' with an unknown option.");
351 
352                     resultReceiver_.append(unknownOptionMsg);
353                     result = OHOS::ERR_INVALID_VALUE;
354                     break;
355                 }
356                 default: {
357                     // 'aa screen' with an unknown option: aa screen -x
358                     // 'aa screen' with an unknown option: aa screen -xxx
359                     std::string unknownOption = "";
360                     std::string unknownOptionMsg = GetUnknownOptionMsg(unknownOption);
361 
362                     HILOG_INFO("'aa screen' with an unknown option.");
363 
364                     resultReceiver_.append(unknownOptionMsg);
365                     result = OHOS::ERR_INVALID_VALUE;
366                     break;
367                 }
368             }
369             break;
370         }
371 
372         switch (option) {
373             case 'h': {
374                 // 'aa screen -h'
375                 // 'aa screen --help'
376                 result = OHOS::ERR_INVALID_VALUE;
377                 break;
378             }
379             case 0: {
380                 break;
381             }
382             default: {
383                 break;
384             }
385         }
386     }
387 
388     if (result != OHOS::ERR_OK) {
389         resultReceiver_.append(HELP_MSG_SCREEN);
390         result = OHOS::ERR_INVALID_VALUE;
391     }
392 
393     return result;
394 }
395 
RunAsStartAbility()396 ErrCode AbilityManagerShellCommand::RunAsStartAbility()
397 {
398     Want want;
399     std::string windowMode;
400     ErrCode result = MakeWantFromCmd(want, windowMode);
401     if (result == OHOS::ERR_OK) {
402         int windowModeKey = std::atoi(windowMode.c_str());
403         if (windowModeKey > 0) {
404             auto setting = AbilityStartSetting::GetEmptySetting();
405             if (setting != nullptr) {
406                 setting->AddProperty(AbilityStartSetting::WINDOW_MODE_KEY, windowMode);
407                 result = AbilityManagerClient::GetInstance()->StartAbility(want, *(setting.get()), nullptr, -1);
408             }
409         } else {
410             result = AbilityManagerClient::GetInstance()->StartAbility(want);
411         }
412         if (result == OHOS::ERR_OK) {
413             HILOG_INFO("%{public}s", STRING_START_ABILITY_OK.c_str());
414             resultReceiver_ = STRING_START_ABILITY_OK + "\n";
415         } else {
416             HILOG_INFO("%{public}s result = %{public}d", STRING_START_ABILITY_NG.c_str(), result);
417             if (result != START_ABILITY_WAITING) {
418                 resultReceiver_ = STRING_START_ABILITY_NG + "\n";
419             }
420             resultReceiver_.append(GetMessageFromCode(result));
421         }
422     } else {
423         resultReceiver_.append(HELP_MSG_START);
424         result = OHOS::ERR_INVALID_VALUE;
425     }
426 
427     return result;
428 }
429 
RunAsStopService()430 ErrCode AbilityManagerShellCommand::RunAsStopService()
431 {
432     ErrCode result = OHOS::ERR_OK;
433 
434     Want want;
435     std::string windowMode;
436     result = MakeWantFromCmd(want, windowMode);
437     if (result == OHOS::ERR_OK) {
438         result = AbilityManagerClient::GetInstance()->StopServiceAbility(want);
439         if (result == OHOS::ERR_OK) {
440             HILOG_INFO("%{public}s", STRING_STOP_SERVICE_ABILITY_OK.c_str());
441             resultReceiver_ = STRING_STOP_SERVICE_ABILITY_OK + "\n";
442         } else {
443             HILOG_INFO("%{public}s result = %{public}d", STRING_STOP_SERVICE_ABILITY_NG.c_str(), result);
444             resultReceiver_ = STRING_STOP_SERVICE_ABILITY_NG + "\n";
445 
446             resultReceiver_.append(GetMessageFromCode(result));
447         }
448     } else {
449         resultReceiver_.append(HELP_MSG_STOP_SERVICE);
450         result = OHOS::ERR_INVALID_VALUE;
451     }
452 
453     return result;
454 }
455 
RunAsDumpsysCommand()456 ErrCode AbilityManagerShellCommand::RunAsDumpsysCommand()
457 {
458     ErrCode result = OHOS::ERR_OK;
459     bool isUserID = false;
460     bool isClient = false;
461     int userID = DEFAULT_INVAL_VALUE;
462     bool isfirstCommand = false;
463     std::string args;
464     for (auto it = argList_.begin(); it != argList_.end(); it++) {
465         if (*it == "-c" || *it == "--client") {
466             if (isClient == false) {
467                 isClient = true;
468             } else {
469                 result = OHOS::ERR_INVALID_VALUE;
470                 resultReceiver_.append(HELP_MSG_DUMPSYS);
471                 return result;
472             }
473         } else if (*it == "-u" || *it == "--userId") {
474             if (it + 1 == argList_.end()) {
475                 result = OHOS::ERR_INVALID_VALUE;
476                 resultReceiver_.append(HELP_MSG_DUMPSYS);
477                 return result;
478             }
479             (void)StrToInt(*(it + 1), userID);
480             if (userID == DEFAULT_INVAL_VALUE) {
481                 result = OHOS::ERR_INVALID_VALUE;
482                 resultReceiver_.append(HELP_MSG_DUMPSYS);
483                 return result;
484             }
485             if (isUserID == false) {
486                 isUserID = true;
487             } else {
488                 result = OHOS::ERR_INVALID_VALUE;
489                 resultReceiver_.append(HELP_MSG_DUMPSYS);
490                 return result;
491             }
492         } else if (*it == std::to_string(userID)) {
493             continue;
494         } else {
495             args += *it;
496             args += " ";
497         }
498     }
499 
500     while (true) {
501         int option = getopt_long(argc_, argv_, SHORT_OPTIONS_DUMPSYS.c_str(), LONG_OPTIONS_DUMPSYS, nullptr);
502 
503         HILOG_INFO("option: %{public}d, optopt: %{public}d, optind: %{public}d", option, optopt, optind);
504 
505         if (optind < 0 || optind > argc_) {
506             resultReceiver_.append(HELP_MSG_DUMPSYS);
507             return OHOS::ERR_INVALID_VALUE;
508         }
509 
510         if (option == -1) {
511             break;
512         }
513 
514         switch (option) {
515             case 'h': {
516                 // 'aa dumpsys -h'
517                 // 'aa dumpsys --help'
518                 resultReceiver_.append(HELP_MSG_DUMPSYS);
519                 result = OHOS::ERR_INVALID_VALUE;
520                 return result;
521             }
522             case 'a': {
523                 if (isfirstCommand == false) {
524                     isfirstCommand = true;
525                 } else {
526                     result = OHOS::ERR_INVALID_VALUE;
527                     resultReceiver_.append(HELP_MSG_DUMPSYS);
528                     return result;
529                 }
530                 // 'aa dumpsys -a'
531                 // 'aa dumpsys --all'
532                 break;
533             }
534             case 'l': {
535                 if (isfirstCommand == false) {
536                     isfirstCommand = true;
537                 } else {
538                     // 'aa dump -i 10 -element -lastpage'
539                     // 'aa dump -i 10 -render -lastpage'
540                     // 'aa dump -i 10 -layer'
541                     if ((optarg != nullptr) && strcmp(optarg, "astpage") && strcmp(optarg, "ayer")) {
542                         result = OHOS::ERR_INVALID_VALUE;
543                         resultReceiver_.append(HELP_MSG_DUMPSYS);
544                         return result;
545                     }
546                 }
547                 // 'aa dumpsys -l'
548                 // 'aa dumpsys --mission-list'
549                 break;
550             }
551             case 'i': {
552                 if (isfirstCommand == false) {
553                     isfirstCommand = true;
554                     int abilityRecordId = DEFAULT_INVAL_VALUE;
555                     (void)StrToInt(optarg, abilityRecordId);
556                     if (abilityRecordId == DEFAULT_INVAL_VALUE) {
557                         result = OHOS::ERR_INVALID_VALUE;
558                         resultReceiver_.append(HELP_MSG_DUMPSYS);
559                         return result;
560                     }
561                 } else {
562                     // 'aa dumpsys -i 10 -inspector'
563                     if ((optarg != nullptr) && strcmp(optarg, "nspector")) {
564                         result = OHOS::ERR_INVALID_VALUE;
565                         resultReceiver_.append(HELP_MSG_DUMPSYS);
566                         return result;
567                     }
568                 }
569                 // 'aa dumpsys -i'
570                 // 'aa dumpsys --ability'
571                 break;
572             }
573             case 'e': {
574                 if (isfirstCommand == false && optarg == nullptr) {
575                     isfirstCommand = true;
576                 } else {
577                     // 'aa dumpsys -i 10 -element'
578                     if ((optarg != nullptr) && strcmp(optarg, "lement")) {
579                         result = OHOS::ERR_INVALID_VALUE;
580                         resultReceiver_.append(HELP_MSG_DUMPSYS);
581                         return result;
582                     }
583                 }
584                 // 'aa dumpsys -e'
585                 // 'aa dumpsys --extension'
586                 break;
587             }
588             case 'p': {
589                 if (isfirstCommand == false && optarg == nullptr) {
590                     isfirstCommand = true;
591                 } else {
592                     result = OHOS::ERR_INVALID_VALUE;
593                     resultReceiver_.append(HELP_MSG_DUMPSYS);
594                     return result;
595                 }
596                 // 'aa dumpsys -p'
597                 // 'aa dumpsys --pending'
598                 break;
599             }
600             case 'r': {
601                 if (isfirstCommand == false && optarg == nullptr) {
602                     isfirstCommand = true;
603                 } else {
604                     // 'aa dump -i 10 -render'
605                     // 'aa dump -i 10 -rotation'
606                     // 'aa dump -i 10 -frontend'
607                     if ((optarg != nullptr) && strcmp(optarg, "ender") && strcmp(optarg, "otation") &&
608                         strcmp(optarg, "ontend")) {
609                         result = OHOS::ERR_INVALID_VALUE;
610                         resultReceiver_.append(HELP_MSG_DUMPSYS);
611                         return result;
612                     }
613                 }
614                 // 'aa dumpsys -r'
615                 // 'aa dumpsys --process'
616                 break;
617             }
618             case 'd': {
619                 if (isfirstCommand == false && optarg == nullptr) {
620                     isfirstCommand = true;
621                 } else {
622                     result = OHOS::ERR_INVALID_VALUE;
623                     resultReceiver_.append(HELP_MSG_DUMPSYS);
624                     return result;
625                 }
626                 // 'aa dumpsys -d'
627                 // 'aa dumpsys --data'
628                 break;
629             }
630             case 'u': {
631                 // 'aa dumpsys -u'
632                 // 'aa dumpsys --userId'
633                 break;
634             }
635             case 'c': {
636                 // 'aa dumpsys -c'
637                 // 'aa dumpsys --client'
638                 break;
639             }
640             case '?': {
641                 if (!isfirstCommand) {
642                     HILOG_INFO("'aa %{public}s' with an unknown option.", cmd_.c_str());
643                     std::string unknownOption = "";
644                     std::string unknownOptionMsg = GetUnknownOptionMsg(unknownOption);
645                     resultReceiver_.append(unknownOptionMsg);
646                     resultReceiver_.append(HELP_MSG_DUMPSYS);
647                     result = OHOS::ERR_INVALID_VALUE;
648                     return result;
649                 }
650                 break;
651             }
652             default: {
653                 HILOG_INFO("'aa %{public}s' with an unknown option.", cmd_.c_str());
654                 std::string unknownOption = "";
655                 std::string unknownOptionMsg = GetUnknownOptionMsg(unknownOption);
656                 resultReceiver_.append(unknownOptionMsg);
657                 result = OHOS::ERR_INVALID_VALUE;
658                 break;
659             }
660         }
661     }
662 
663     if (result != OHOS::ERR_OK) {
664         resultReceiver_.append(HELP_MSG_DUMPSYS);
665     } else {
666         if (isfirstCommand != true) {
667             result = OHOS::ERR_INVALID_VALUE;
668             resultReceiver_.append(HELP_MSG_NO_OPTION + "\n");
669             resultReceiver_.append(HELP_MSG_DUMPSYS);
670             return result;
671         }
672 
673         std::vector<std::string> dumpResults;
674         result = AbilityManagerClient::GetInstance()->DumpSysState(args, dumpResults, isClient, isUserID, userID);
675         if (result == OHOS::ERR_OK) {
676             for (auto it : dumpResults) {
677                 resultReceiver_ += it + "\n";
678             }
679         } else {
680             HILOG_INFO("failed to dump state.");
681         }
682     }
683     return result;
684 }
685 
RunAsForceStop()686 ErrCode AbilityManagerShellCommand::RunAsForceStop()
687 {
688     HILOG_INFO("[%{public}s(%{public}s)] enter", __FILE__, __FUNCTION__);
689     if (argList_.empty()) {
690         resultReceiver_.append(HELP_MSG_FORCE_STOP + "\n");
691         return OHOS::ERR_INVALID_VALUE;
692     }
693     HILOG_INFO("Bundle name : %{public}s", argList_[0].c_str());
694     ErrCode result = OHOS::ERR_OK;
695     result = AbilityManagerClient::GetInstance()->KillProcess(argList_[0]);
696     if (result == OHOS::ERR_OK) {
697         HILOG_INFO("%{public}s", STRING_FORCE_STOP_OK.c_str());
698         resultReceiver_ = STRING_FORCE_STOP_OK + "\n";
699     } else {
700         HILOG_INFO("%{public}s result = %{public}d", STRING_FORCE_STOP_NG.c_str(), result);
701         resultReceiver_ = STRING_FORCE_STOP_NG + "\n";
702         resultReceiver_.append(GetMessageFromCode(result));
703     }
704     return result;
705 }
706 
RunAsAttachDebugCommand()707 ErrCode AbilityManagerShellCommand::RunAsAttachDebugCommand()
708 {
709     HILOG_DEBUG("Called.");
710     std::string bundleName = "";
711     ParseBundleName(bundleName);
712     if (bundleName.empty()) {
713         resultReceiver_.append(HELP_MSG_ATTACH_APP_DEBUG + "\n");
714         return OHOS::ERR_INVALID_VALUE;
715     }
716 
717     auto result = AbilityManagerClient::GetInstance()->AttachAppDebug(bundleName);
718     if (result == OHOS::ERR_OK) {
719         resultReceiver_.append(STRING_ATTACH_APP_DEBUG_OK + "\n");
720         return result;
721     }
722 
723     HILOG_DEBUG("%{public}s result = %{public}d", STRING_ATTACH_APP_DEBUG_NG.c_str(), result);
724     resultReceiver_.append(STRING_ATTACH_APP_DEBUG_NG + "\n");
725     return result;
726 }
727 
RunAsDetachDebugCommand()728 ErrCode AbilityManagerShellCommand::RunAsDetachDebugCommand()
729 {
730     HILOG_DEBUG("Called.");
731     std::string bundleName = "";
732     ParseBundleName(bundleName);
733     if (bundleName.empty()) {
734         resultReceiver_.append(HELP_MSG_DETACH_APP_DEBUG + "\n");
735         return OHOS::ERR_INVALID_VALUE;
736     }
737 
738     auto result = AbilityManagerClient::GetInstance()->DetachAppDebug(bundleName);
739     if (result == OHOS::ERR_OK) {
740         resultReceiver_.append(STRING_DETACH_APP_DEBUG_OK + "\n");
741         return result;
742     }
743 
744     HILOG_DEBUG("%{public}s result = %{public}d", STRING_DETACH_APP_DEBUG_NG.c_str(), result);
745     resultReceiver_.append(STRING_DETACH_APP_DEBUG_NG + "\n");
746     return result;
747 }
748 
RunAsProcessCommand()749 ErrCode AbilityManagerShellCommand::RunAsProcessCommand()
750 {
751     Want want;
752     ErrCode result = MakeWantForProcess(want);
753     if (result == OHOS::ERR_OK) {
754         auto appMgrClient = std::make_shared<AppMgrClient>();
755         result = appMgrClient->StartNativeProcessForDebugger(want);
756         if (result == OHOS::ERR_OK) {
757             HILOG_INFO("%{public}s", STRING_START_NATIVE_PROCESS_OK.c_str());
758             resultReceiver_ = STRING_START_NATIVE_PROCESS_OK;
759         } else {
760             HILOG_INFO("%{public}s result = %{public}d", STRING_START_NATIVE_PROCESS_NG.c_str(), result);
761             resultReceiver_ = STRING_START_NATIVE_PROCESS_NG;
762         }
763     } else {
764         resultReceiver_.append(HELP_MSG_PROCESS);
765         result = OHOS::ERR_INVALID_VALUE;
766     }
767 
768     return result;
769 }
770 
MatchOrderString(const std::regex & regexScript,const std::string & orderCmd)771 bool AbilityManagerShellCommand::MatchOrderString(const std::regex &regexScript, const std::string &orderCmd)
772 {
773     HILOG_DEBUG("order string is %{public}s", orderCmd.c_str());
774     if (orderCmd.empty()) {
775         HILOG_ERROR("input param order string is empty");
776         return false;
777     }
778 
779     std::match_results<std::string::const_iterator> matchResults;
780     if (!std::regex_match(orderCmd, matchResults, regexScript)) {
781         HILOG_ERROR("the order not match");
782         return false;
783     }
784 
785     return true;
786 }
787 
CheckPerfCmdString(const char * optarg,const size_t paramLength,std::string & perfCmd)788 bool AbilityManagerShellCommand::CheckPerfCmdString(
789     const char* optarg, const size_t paramLength, std::string &perfCmd)
790 {
791     if (optarg == nullptr) {
792         HILOG_ERROR("input param optarg is nullptr");
793         return false;
794     }
795 
796     if (strlen(optarg) >= paramLength) {
797         HILOG_ERROR("debuggablePipe aa start -p param length must be less than 1024.");
798         return false;
799     }
800 
801     perfCmd = optarg;
802     const std::regex regexDumpHeapType(R"(^\s*(dumpheap)\s*$)");
803     const std::regex regexSleepType(R"(^\s*(sleep)((\s+\d*)|)\s*$)");
804     if (MatchOrderString(regexDumpHeapType, perfCmd) || MatchOrderString(regexSleepType, perfCmd)) {
805         return true;
806     }
807 
808     HILOG_DEBUG("the command not match");
809     const std::regex regexProfileType(R"(^\s*(profile)\s+(nativeperf|jsperf)(\s+.*|$))");
810     if (!MatchOrderString(regexProfileType, perfCmd)) {
811         HILOG_ERROR("the command is invalid");
812         return false;
813     }
814 
815     auto findPos = perfCmd.find("jsperf");
816     if (findPos != std::string::npos) {
817         const std::regex regexCmd(R"(^jsperf($|\s+($|((5000|([1-9]|[1-4]\d)\d\d)|)\s*($|nativeperf.*))))");
818         if (!MatchOrderString(regexCmd, perfCmd.substr(findPos, perfCmd.length() - findPos))) {
819             HILOG_ERROR("the order is invalid");
820             return false;
821         }
822     }
823     return true;
824 }
825 
IsNum(const std::string & s)826 bool IsNum(const std::string& s)
827 {
828     for (auto c : s)
829         if (!std::isdigit(c))
830             return false;
831     return true;
832 }
833 
CheckParameters(int extraArguments)834 bool AbilityManagerShellCommand::CheckParameters(int extraArguments)
835 {
836     if (optind + extraArguments >= argc_) return false;
837     int index = optind + 1; // optind is the index of 'start' which is right behind optarg
838     int count = 0;
839     while (index < argc_ && argv_[index][0] != '-') {
840         count++;
841         index++;
842     }
843     return count == extraArguments;
844 }
845 
846 // parse integer parameters
ParseParam(ParametersInteger & pi)847 ErrCode AbilityManagerShellCommand::ParseParam(ParametersInteger& pi)
848 {
849     std::string key = optarg;
850     std::string intString = argv_[optind + OPTION_PARAMETER_VALUE_OFFSET];
851     if (!IsNum(intString)) {
852         resultReceiver_.append("invalid parameter ");
853         resultReceiver_.append(intString);
854         resultReceiver_.append(" for integer option\n");
855 
856         return OHOS::ERR_INVALID_VALUE;
857     }
858     pi[key] = atoi(argv_[optind + OPTION_PARAMETER_VALUE_OFFSET]);
859     return OHOS::ERR_OK;
860 }
861 
862 // parse string parameters
ParseParam(ParametersString & ps,bool isNull=false)863 ErrCode AbilityManagerShellCommand::ParseParam(ParametersString& ps, bool isNull = false)
864 {
865     std::string key = optarg;
866     std::string value = "";
867     if (!isNull)
868         value = argv_[optind + OPTION_PARAMETER_VALUE_OFFSET];
869 
870     ps[key] = value;
871 
872     return OHOS::ERR_OK;
873 }
874 
875 // parse bool parameters
ParseParam(ParametersBool & pb)876 ErrCode AbilityManagerShellCommand::ParseParam(ParametersBool& pb)
877 {
878     std::string key = optarg;
879     std::string boolString = argv_[optind + OPTION_PARAMETER_VALUE_OFFSET];
880     std::transform(boolString.begin(), boolString.end(), boolString.begin(), ::tolower);
881     bool value;
882     if (boolString == "true" || boolString == "t") {
883         value = true;
884     } else if (boolString == "false" || boolString == "f") {
885         value = false;
886     } else {
887         resultReceiver_.append("invalid parameter ");
888         resultReceiver_.append(argv_[optind + OPTION_PARAMETER_VALUE_OFFSET]);
889         resultReceiver_.append(" for bool option\n");
890 
891         return OHOS::ERR_INVALID_VALUE;
892     }
893 
894     pb[key] = value;
895 
896     return OHOS::ERR_OK;
897 }
898 
SetParams(const ParametersInteger & pi,Want & want)899 void AbilityManagerShellCommand::SetParams(const ParametersInteger& pi, Want& want)
900 {
901     for (auto it = pi.begin(); it != pi.end(); it++) {
902         want.SetParam(it->first, it->second);
903     }
904 }
905 
SetParams(const ParametersString & ps,Want & want)906 void AbilityManagerShellCommand::SetParams(const ParametersString& ps, Want& want)
907 {
908     for (auto it = ps.begin(); it != ps.end(); it++) {
909         want.SetParam(it->first, it->second);
910     }
911 }
912 
SetParams(const ParametersBool & pb,Want & want)913 void AbilityManagerShellCommand::SetParams(const ParametersBool& pb, Want& want)
914 {
915     for (auto it = pb.begin(); it != pb.end(); it++) {
916         want.SetParam(it->first, it->second);
917     }
918 }
919 
AddEntities(const std::vector<std::string> & entities,Want & want)920 void AddEntities(const std::vector<std::string>& entities, Want& want)
921 {
922     for (auto entity : entities)
923         want.AddEntity(entity);
924 }
925 
MakeWantForProcess(Want & want)926 ErrCode AbilityManagerShellCommand::MakeWantForProcess(Want& want)
927 {
928     int result = OHOS::ERR_OK;
929     int option = -1;
930     int counter = 0;
931     std::string deviceId = "";
932     std::string bundleName = "";
933     std::string abilityName = "";
934     std::string moduleName = "";
935     std::string perfCmd = "";
936     std::string debugCmd = "";
937     bool isPerf = false;
938     bool isSandboxApp = false;
939 
940     while (true) {
941         counter++;
942 
943         option = getopt_long(argc_, argv_, SHORT_OPTIONS_PROCESS.c_str(), LONG_OPTIONS_PROCESS, nullptr);
944 
945         HILOG_INFO("option: %{public}d, optopt: %{public}d, optind: %{public}d", option, optopt, optind);
946 
947         if (optind < 0 || optind > argc_) {
948             return OHOS::ERR_INVALID_VALUE;
949         }
950 
951         if (option == -1) {
952             // When scanning the first argument
953             if (counter == 1 && strcmp(argv_[optind], cmd_.c_str()) == 0) {
954                 // 'aa process' with no option: aa process
955                 // 'aa process' with a wrong argument: aa process xxx
956                 HILOG_INFO("'aa %{public}s' %{public}s!", HELP_MSG_NO_OPTION.c_str(), cmd_.c_str());
957 
958                 resultReceiver_.append(HELP_MSG_NO_OPTION + "\n");
959                 result = OHOS::ERR_INVALID_VALUE;
960             }
961             break;
962         }
963 
964         if (option == '?') {
965             switch (optopt) {
966                 case 'a': {
967                     // 'aa process -a' with no argument
968                     HILOG_INFO("'aa %{public}s -a' with no argument.", cmd_.c_str());
969 
970                     resultReceiver_.append("error: option ");
971                     resultReceiver_.append("requires a value.\n");
972 
973                     result = OHOS::ERR_INVALID_VALUE;
974                     break;
975                 }
976                 case 'b': {
977                     // 'aa process -b' with no argument
978                     HILOG_INFO("'aa %{public}s -b' with no argument.", cmd_.c_str());
979 
980                     resultReceiver_.append("error: option ");
981                     resultReceiver_.append("requires a value.\n");
982 
983                     result = OHOS::ERR_INVALID_VALUE;
984                     break;
985                 }
986                 case 'm': {
987                     // 'aa process -m' with no argument
988                     HILOG_INFO("'aa %{public}s -m' with no argument.", cmd_.c_str());
989 
990                     resultReceiver_.append("error: option ");
991                     resultReceiver_.append("requires a value.\n");
992 
993                     result = OHOS::ERR_INVALID_VALUE;
994                     break;
995                 }
996                 case 'p': {
997                     // 'aa process -p' with no argument
998                     HILOG_INFO("'aa %{public}s -p' with no argument.", cmd_.c_str());
999 
1000                     resultReceiver_.append("error: option ");
1001                     resultReceiver_.append("requires a value.\n");
1002 
1003                     result = OHOS::ERR_INVALID_VALUE;
1004                     break;
1005                 }
1006                 case 'D': {
1007                     // 'aa process -D' with no argument
1008                     HILOG_INFO("'aa %{public}s -D' with no argument.", cmd_.c_str());
1009 
1010                     resultReceiver_.append("error: option ");
1011                     resultReceiver_.append("requires a value.\n");
1012 
1013                     result = OHOS::ERR_INVALID_VALUE;
1014                     break;
1015                 }
1016                 case 0: {
1017                     // 'aa process' with an unknown option: aa process --x
1018                     // 'aa process' with an unknown option: aa process --xxx
1019                     std::string unknownOption = "";
1020                     std::string unknownOptionMsg = GetUnknownOptionMsg(unknownOption);
1021 
1022                     HILOG_INFO("'aa %{public}s' with an unknown option.", cmd_.c_str());
1023 
1024                     resultReceiver_.append(unknownOptionMsg);
1025                     result = OHOS::ERR_INVALID_VALUE;
1026                     break;
1027                 }
1028                 default: {
1029                     // 'aa process' with an unknown option: aa process -x
1030                     // 'aa process' with an unknown option: aa process -xxx
1031                     std::string unknownOption = "";
1032                     std::string unknownOptionMsg = GetUnknownOptionMsg(unknownOption);
1033 
1034                     HILOG_INFO("'aa %{public}s' with an unknown option.", cmd_.c_str());
1035 
1036                     resultReceiver_.append(unknownOptionMsg);
1037                     result = OHOS::ERR_INVALID_VALUE;
1038                     break;
1039                 }
1040             }
1041             break;
1042         }
1043 
1044         switch (option) {
1045             case 'h': {
1046                 // 'aa process -h'
1047                 // 'aa process --help'
1048                 result = OHOS::ERR_INVALID_VALUE;
1049                 break;
1050             }
1051             case 'a': {
1052                 // 'aa process -a xxx'
1053                 // save ability name
1054                 abilityName = optarg;
1055                 break;
1056             }
1057             case 'b': {
1058                 // 'aa process -b xxx'
1059                 // save bundle name
1060                 bundleName = optarg;
1061                 break;
1062             }
1063             case 'm': {
1064                 // 'aa process -m xxx'
1065                 // save module name
1066                 moduleName = optarg;
1067                 break;
1068             }
1069             case 'p': {
1070                 // 'aa process -p xxx'
1071                 // save perf cmd
1072                 if (strlen(optarg) < PARAM_LENGTH) {
1073                     perfCmd = optarg;
1074                     isPerf = true;
1075                 }
1076                 break;
1077             }
1078             case 'D': {
1079                 // 'aa process -D xxx'
1080                 // save debug cmd
1081                 if (!isPerf && strlen(optarg) < PARAM_LENGTH) {
1082                     HILOG_INFO("debug cmd.");
1083                     debugCmd = optarg;
1084                 }
1085                 break;
1086             }
1087             case 'S': {
1088                 // 'aa process -S'
1089                 // enter sanbox to perform app
1090                 isSandboxApp = true;
1091                 break;
1092             }
1093             case 0: {
1094                 break;
1095             }
1096             default: {
1097                 break;
1098             }
1099         }
1100     }
1101 
1102     if (result == OHOS::ERR_OK) {
1103         if (perfCmd.empty() && debugCmd.empty()) {
1104             HILOG_INFO("debuggablePipe aa process must contains -p or -D and param length must be less than 1024.");
1105             return OHOS::ERR_INVALID_VALUE;
1106         }
1107 
1108         if (abilityName.size() == 0 || bundleName.size() == 0) {
1109             // 'aa process -a <ability-name> -b <bundle-name> [-D]'
1110             HILOG_INFO("'aa %{public}s' without enough options.", cmd_.c_str());
1111 
1112             if (abilityName.size() == 0) {
1113                 resultReceiver_.append(HELP_MSG_NO_ABILITY_NAME_OPTION + "\n");
1114             }
1115 
1116             if (bundleName.size() == 0) {
1117                 resultReceiver_.append(HELP_MSG_NO_BUNDLE_NAME_OPTION + "\n");
1118             }
1119 
1120             result = OHOS::ERR_INVALID_VALUE;
1121         } else {
1122             ElementName element(deviceId, bundleName, abilityName, moduleName);
1123             want.SetElement(element);
1124 
1125             if (!perfCmd.empty()) {
1126                 want.SetParam("perfCmd", perfCmd);
1127             }
1128             if (!debugCmd.empty()) {
1129                 want.SetParam("debugCmd", debugCmd);
1130             }
1131             if (isSandboxApp) {
1132                 want.SetParam("sandboxApp", isSandboxApp);
1133             }
1134         }
1135     }
1136 
1137     return result;
1138 }
1139 
ParseBundleName(std::string & bundleName)1140 void AbilityManagerShellCommand::ParseBundleName(std::string &bundleName)
1141 {
1142     int option = -1;
1143     int counter = 0;
1144 
1145     while (true) {
1146         counter++;
1147         option = getopt_long(argc_, argv_, SHORT_OPTIONS_ATTACH.c_str(), LONG_OPTIONS_ATTACH, nullptr);
1148         HILOG_DEBUG("getopt_long option: %{public}d, optopt: %{public}d, optind: %{public}d", option, optopt, optind);
1149 
1150         if (optind < 0 || optind > argc_) {
1151             break;
1152         }
1153 
1154         if (option == -1) {
1155             // aa command without option
1156             if (counter == 1 && strcmp(argv_[optind], cmd_.c_str()) == 0) {
1157                 resultReceiver_.append(HELP_MSG_NO_OPTION + "\n");
1158             }
1159             break;
1160         }
1161 
1162         if (option == '?') {
1163             switch (optopt) {
1164                 case 'b':
1165                 case 'h':
1166                     break;
1167                 default: {
1168                     // 'aa attach/detach' with an unknown option
1169                     std::string unknownOption = "";
1170                     std::string unknownOptionMsg = GetUnknownOptionMsg(unknownOption);
1171                     resultReceiver_.append(unknownOptionMsg);
1172                     break;
1173                 }
1174             }
1175             break;
1176         }
1177 
1178         switch (option) {
1179             case 'b': {
1180                 bundleName = optarg;
1181                 break;
1182             }
1183             default:
1184                 break;
1185         }
1186     }
1187 }
1188 
1189 #ifdef ABILITY_COMMAND_FOR_TEST
RunForceTimeoutForTest()1190 ErrCode AbilityManagerShellCommand::RunForceTimeoutForTest()
1191 {
1192     HILOG_INFO("[%{public}s(%{public}s)] enter", __FILE__, __FUNCTION__);
1193     if (argList_.empty()) {
1194         resultReceiver_.append(HELP_MSG_FORCE_TIMEOUT + "\n");
1195         return OHOS::ERR_INVALID_VALUE;
1196     }
1197 
1198     ErrCode result = OHOS::ERR_OK;
1199     if (argList_.size() == NUMBER_ONE && argList_[0] == HELP_MSG_FORCE_TIMEOUT_CLEAN) {
1200         HILOG_INFO("clear ability timeout flags.");
1201         result = AbilityManagerClient::GetInstance()->ForceTimeoutForTest(argList_[0], "");
1202     } else if (argList_.size() == NUMBER_TWO) {
1203         HILOG_INFO("Ability name : %{public}s, state: %{public}s", argList_[0].c_str(), argList_[1].c_str());
1204         result = AbilityManagerClient::GetInstance()->ForceTimeoutForTest(argList_[0], argList_[1]);
1205     } else {
1206         resultReceiver_.append(HELP_MSG_FORCE_TIMEOUT + "\n");
1207         return OHOS::ERR_INVALID_VALUE;
1208     }
1209     if (result == OHOS::ERR_OK) {
1210         HILOG_INFO("%{public}s", STRING_FORCE_TIMEOUT_OK.c_str());
1211         resultReceiver_ = STRING_FORCE_TIMEOUT_OK + "\n";
1212     } else {
1213         HILOG_INFO("%{public}s result = %{public}d", STRING_FORCE_TIMEOUT_NG.c_str(), result);
1214         resultReceiver_ = STRING_FORCE_TIMEOUT_NG + "\n";
1215         resultReceiver_.append(GetMessageFromCode(result));
1216     }
1217     return result;
1218 }
1219 #endif
1220 
MakeWantFromCmd(Want & want,std::string & windowMode)1221 ErrCode AbilityManagerShellCommand::MakeWantFromCmd(Want& want, std::string& windowMode)
1222 {
1223     int result = OHOS::ERR_OK;
1224 
1225     int option = -1;
1226     int counter = 0;
1227 
1228     std::string deviceId = "";
1229     std::string bundleName = "";
1230     std::string abilityName = "";
1231     std::string moduleName;
1232     std::string perfCmd;
1233     ParametersInteger parametersInteger;
1234     ParametersString parametersString;
1235     ParametersBool parametersBool;
1236     std::string uri;
1237     std::string action;
1238     std::vector<std::string> entities;
1239     std::string typeVal;
1240     bool isColdStart = false;
1241     bool isDebugApp = false;
1242     bool isContinuation = false;
1243     bool isSandboxApp = false;
1244     bool isNativeDebug = false;
1245 
1246     while (true) {
1247         counter++;
1248 
1249         option = getopt_long(argc_, argv_, SHORT_OPTIONS.c_str(), LONG_OPTIONS, nullptr);
1250 
1251         HILOG_INFO("option: %{public}d, optopt: %{public}d, optind: %{public}d", option, optopt, optind);
1252 
1253         if (optind < 0 || optind > argc_) {
1254             return OHOS::ERR_INVALID_VALUE;
1255         }
1256 
1257         if (option == -1) {
1258             // When scanning the first argument
1259             if (counter == 1 && strcmp(argv_[optind], cmd_.c_str()) == 0) {
1260                 // 'aa start' with no option: aa start
1261                 // 'aa start' with a wrong argument: aa start xxx
1262                 // 'aa stop-service' with no option: aa stop-service
1263                 // 'aa stop-service' with a wrong argument: aa stop-service xxx
1264                 HILOG_INFO("'aa %{public}s' %{public}s", HELP_MSG_NO_OPTION.c_str(), cmd_.c_str());
1265 
1266                 resultReceiver_.append(HELP_MSG_NO_OPTION + "\n");
1267                 result = OHOS::ERR_INVALID_VALUE;
1268             }
1269             break;
1270         }
1271 
1272         if (option == '?') {
1273             switch (optopt) {
1274                 case 'h': {
1275                     // 'aa start -h'
1276                     // 'aa stop-service -h'
1277                     result = OHOS::ERR_INVALID_VALUE;
1278                     break;
1279                 }
1280                 case 'd': {
1281                     // 'aa start -d' with no argument
1282                     // 'aa stop-service -d' with no argument
1283                     HILOG_INFO("'aa %{public}s -d' with no argument.", cmd_.c_str());
1284 
1285                     resultReceiver_.append("error: option ");
1286                     resultReceiver_.append("requires a value.\n");
1287 
1288                     result = OHOS::ERR_INVALID_VALUE;
1289                     break;
1290                 }
1291                 case 'a': {
1292                     // 'aa start -a' with no argument
1293                     // 'aa stop-service -a' with no argument
1294                     HILOG_INFO("'aa %{public}s -a' with no argument.", cmd_.c_str());
1295 
1296                     resultReceiver_.append("error: option ");
1297                     resultReceiver_.append("requires a value.\n");
1298 
1299                     result = OHOS::ERR_INVALID_VALUE;
1300                     break;
1301                 }
1302                 case 'b': {
1303                     // 'aa start -b' with no argument
1304                     // 'aa stop-service -b' with no argument
1305                     HILOG_INFO("'aa %{public}s -b' with no argument.", cmd_.c_str());
1306 
1307                     resultReceiver_.append("error: option ");
1308                     resultReceiver_.append("requires a value.\n");
1309 
1310                     result = OHOS::ERR_INVALID_VALUE;
1311                     break;
1312                 }
1313                 case 'e': {
1314                     // 'aa start -e' with no argument
1315                     HILOG_INFO("'aa %{public}s -e with no argument.", cmd_.c_str());
1316 
1317                     resultReceiver_.append("error: option ");
1318                     resultReceiver_.append("requires a value.\n");
1319 
1320                     result = OHOS::ERR_INVALID_VALUE;
1321                     break;
1322                 }
1323                 case 't': {
1324                     // 'aa start -t' with no argument
1325                     HILOG_INFO("'aa %{public}s -t with no argument.", cmd_.c_str());
1326 
1327                     resultReceiver_.append("error: option ");
1328                     resultReceiver_.append("requires a value.\n");
1329 
1330                     result = OHOS::ERR_INVALID_VALUE;
1331                     break;
1332                 }
1333                 case 's': {
1334                     // 'aa start -s' with no argument
1335                     // 'aa stop-service -s' with no argument
1336                     HILOG_INFO("'aa %{public}s -s' with no argument.", cmd_.c_str());
1337 
1338                     resultReceiver_.append("error: option ");
1339                     resultReceiver_.append(argv_[optind - 1]);
1340                     resultReceiver_.append("' requires a value.\n");
1341 
1342                     result = OHOS::ERR_INVALID_VALUE;
1343                     break;
1344                 }
1345                 case 'm': {
1346                     // 'aa start -m' with no argument
1347                     // 'aa stop-service -m' with no argument
1348                     HILOG_INFO("'aa %{public}s -m' with no argument.", cmd_.c_str());
1349 
1350                     resultReceiver_.append("error: option ");
1351                     resultReceiver_.append("requires a value.\n");
1352 
1353                     result = OHOS::ERR_INVALID_VALUE;
1354                     break;
1355                 }
1356                 case 'p': {
1357                     // 'aa start -p' with no argument
1358                     // 'aa stop-service -p' with no argument
1359                     HILOG_INFO("'aa %{public}s -p' with no argument.", cmd_.c_str());
1360 
1361                     resultReceiver_.append("error: option ");
1362                     resultReceiver_.append("requires a value.\n");
1363 
1364                     result = OHOS::ERR_INVALID_VALUE;
1365                     break;
1366                 }
1367                 case OPTION_PARAMETER_INTEGER: {
1368                     // 'aa start --pi' with no argumnet
1369                     HILOG_INFO("'aa %{public}s --pi' with no argument.", cmd_.c_str());
1370 
1371                     resultReceiver_.append("error: option ");
1372                     resultReceiver_.append("requires a value.\n");
1373 
1374                     result = OHOS::ERR_INVALID_VALUE;
1375 
1376                     break;
1377                 }
1378                 case OPTION_PARAMETER_STRING: {
1379                     // 'aa start --ps' with no argumnet
1380                     HILOG_INFO("'aa %{public}s --ps' with no argument.", cmd_.c_str());
1381 
1382                     resultReceiver_.append("error: option ");
1383                     resultReceiver_.append("requires a value.\n");
1384 
1385                     result = OHOS::ERR_INVALID_VALUE;
1386 
1387                     break;
1388                 }
1389                 case OPTION_PARAMETER_BOOL: {
1390                     // 'aa start --pb' with no argumnet
1391                     HILOG_INFO("'aa %{public}s -pb' with no argument.", cmd_.c_str());
1392 
1393                     resultReceiver_.append("error: option ");
1394                     resultReceiver_.append("requires a value.\n");
1395 
1396                     result = OHOS::ERR_INVALID_VALUE;
1397 
1398                     break;
1399                 }
1400                 case OPTION_PARAMETER_NULL_STRING: {
1401                     // 'aa start --psn' with no argumnet
1402                     HILOG_INFO("'aa %{public}s --psn' with no argument.", cmd_.c_str());
1403 
1404                     resultReceiver_.append("error: option ");
1405                     resultReceiver_.append("requires a value.\n");
1406 
1407                     result = OHOS::ERR_INVALID_VALUE;
1408 
1409                     break;
1410                 }
1411 
1412                 case 'A': {
1413                     // 'aa start -A' with no argumnet
1414                     HILOG_INFO("'aa %{public}s -A' with no argument.", cmd_.c_str());
1415 
1416                     resultReceiver_.append("error: option ");
1417                     resultReceiver_.append("requires a value.\n");
1418 
1419                     result = OHOS::ERR_INVALID_VALUE;
1420 
1421                     break;
1422                 }
1423                 case 'U': {
1424                     // 'aa start -U' with no argumnet
1425                     HILOG_INFO("'aa %{public}s -U' with no argument.", cmd_.c_str());
1426 
1427                     resultReceiver_.append("error: option ");
1428                     resultReceiver_.append("requires a value.\n");
1429 
1430                     result = OHOS::ERR_INVALID_VALUE;
1431 
1432                     break;
1433                 }
1434                 case 0: {
1435                     // 'aa start' with an unknown option: aa start --x
1436                     // 'aa start' with an unknown option: aa start --xxx
1437                     // 'aa stop-service' with an unknown option: aa stop-service --x
1438                     // 'aa stop-service' with an unknown option: aa stop-service --xxx
1439                     std::string unknownOption = "";
1440                     std::string unknownOptionMsg = GetUnknownOptionMsg(unknownOption);
1441 
1442                     HILOG_INFO("'aa %{public}s' with an unknown option.", cmd_.c_str());
1443 
1444                     resultReceiver_.append(unknownOptionMsg);
1445                     result = OHOS::ERR_INVALID_VALUE;
1446                     break;
1447                 }
1448                 default: {
1449                     // 'aa start' with an unknown option: aa start -x
1450                     // 'aa start' with an unknown option: aa start -xxx
1451                     // 'aa stop-service' with an unknown option: aa stop-service -x
1452                     // 'aa stop-service' with an unknown option: aa stop-service -xxx
1453                     std::string unknownOption = "";
1454                     std::string unknownOptionMsg = GetUnknownOptionMsg(unknownOption);
1455 
1456                     HILOG_INFO("'aa %{public}s' with an unknown option.", cmd_.c_str());
1457 
1458                     resultReceiver_.append(unknownOptionMsg);
1459                     result = OHOS::ERR_INVALID_VALUE;
1460                     break;
1461                 }
1462             }
1463             break;
1464         }
1465 
1466         switch (option) {
1467             case 'h': {
1468                 // 'aa start -h'
1469                 // 'aa start --help'
1470                 // 'aa stop-service -h'
1471                 // 'aa stop-service --help'
1472                 result = OHOS::ERR_INVALID_VALUE;
1473                 break;
1474             }
1475             case 'd': {
1476                 // 'aa start -d xxx'
1477                 // 'aa stop-service -d xxx'
1478 
1479                 // save device ID
1480                 if (optarg != nullptr) {
1481                     deviceId = optarg;
1482                 }
1483                 break;
1484             }
1485             case 'a': {
1486                 // 'aa start -a xxx'
1487                 // 'aa stop-service -a xxx'
1488 
1489                 // save ability name
1490                 abilityName = optarg;
1491                 break;
1492             }
1493             case 'b': {
1494                 // 'aa start -b xxx'
1495                 // 'aa stop-service -b xxx'
1496 
1497                 // save bundle name
1498                 bundleName = optarg;
1499                 break;
1500             }
1501             case 'e': {
1502                 // 'aa start -e xxx'
1503 
1504                 // save entity
1505                 entities.push_back(optarg);
1506                 break;
1507             }
1508             case 't': {
1509                 // 'aa start -t xxx'
1510 
1511                 // save type
1512                 typeVal = optarg;
1513                 break;
1514             }
1515             case 's': {
1516                 // 'aa start -s xxx'
1517                 // save windowMode
1518                 windowMode = optarg;
1519                 break;
1520             }
1521             case 'm': {
1522                 // 'aa start -m xxx'
1523                 // 'aa stop-service -m xxx'
1524 
1525                 // save module name
1526                 moduleName = optarg;
1527                 break;
1528             }
1529             case 'p': {
1530                 // 'aa start -p xxx'
1531                 // 'aa stop-service -p xxx'
1532 
1533                 // save module name
1534                 if (!CheckPerfCmdString(optarg, PARAM_LENGTH, perfCmd)) {
1535                     HILOG_ERROR("input perfCmd is invalid %{public}s", perfCmd.c_str());
1536                     result = OHOS::ERR_INVALID_VALUE;
1537                 }
1538                 break;
1539             }
1540             case OPTION_PARAMETER_INTEGER: {
1541                 // 'aa start --pi xxx'
1542                 if (!CheckParameters(EXTRA_ARGUMENTS_FOR_KEY_VALUE_PAIR)) {
1543                     resultReceiver_.append("invalid number of parameters for option --pi\n");
1544                     result = OHOS::ERR_INVALID_VALUE;
1545                     break;
1546                 }
1547 
1548                 // parse option arguments into a key-value map
1549                 result = ParseParam(parametersInteger);
1550 
1551                 optind++;
1552 
1553                 break;
1554             }
1555             case OPTION_PARAMETER_STRING: {
1556                 // 'aa start --ps xxx'
1557                 if (!CheckParameters(EXTRA_ARGUMENTS_FOR_KEY_VALUE_PAIR)) {
1558                     resultReceiver_.append("invalid number of parameters for option --ps\n");
1559                     result = OHOS::ERR_INVALID_VALUE;
1560                     break;
1561                 }
1562 
1563                 // parse option arguments into a key-value map
1564                 result = ParseParam(parametersString);
1565 
1566                 optind++;
1567 
1568                 break;
1569             }
1570             case OPTION_PARAMETER_BOOL: {
1571                 // 'aa start --pb xxx'
1572                 if (!CheckParameters(EXTRA_ARGUMENTS_FOR_KEY_VALUE_PAIR)) {
1573                     resultReceiver_.append("invalid number of parameters for option --pb\n");
1574                     result = OHOS::ERR_INVALID_VALUE;
1575                     break;
1576                 }
1577 
1578                 // parse option arguments into a key-value map
1579                 result = ParseParam(parametersBool);
1580 
1581                 optind++;
1582 
1583                 break;
1584             }
1585             case OPTION_PARAMETER_NULL_STRING: {
1586                 // 'aa start --psn xxx'
1587                 if (!CheckParameters(EXTRA_ARGUMENTS_FOR_NULL_STRING)) {
1588                     resultReceiver_.append("invalid number of parameters for option --psn\n");
1589                     result = OHOS::ERR_INVALID_VALUE;
1590                     break;
1591                 }
1592 
1593                 // parse option arguments into a key-value map
1594                 result = ParseParam(parametersString, true);
1595 
1596                 break;
1597             }
1598             case 'U': {
1599                 // 'aa start -U xxx'
1600 
1601                 // save URI
1602                 uri = optarg;
1603                 break;
1604             }
1605             case 'A': {
1606                 // 'aa start -A xxx'
1607 
1608                 // save action
1609                 action = optarg;
1610                 break;
1611             }
1612             case 'C': {
1613                 // 'aa start -C'
1614                 // cold start app
1615                 isColdStart = true;
1616                 break;
1617             }
1618             case 'D': {
1619                 // 'aa start -D'
1620                 // debug app
1621                 isDebugApp = true;
1622                 break;
1623             }
1624             case 'S': {
1625                 // 'aa start -b <bundleName> -a <abilityName> -p <perf-cmd> -S'
1626                 // enter sanbox to perform app
1627                 isSandboxApp = true;
1628                 break;
1629             }
1630             case 'c': {
1631                 // 'aa start -c'
1632                 // set ability launch reason = continuation
1633                 isContinuation = true;
1634                 break;
1635             }
1636             case 'N': {
1637                 // 'aa start -N'
1638                 // wait for debug in appspawn
1639                 isNativeDebug = true;
1640                 break;
1641             }
1642             case 0: {
1643                 break;
1644             }
1645             default: {
1646                 break;
1647             }
1648         }
1649     }
1650 
1651     if (result == OHOS::ERR_OK) {
1652         if (abilityName.size() == 0 || bundleName.size() == 0) {
1653             // 'aa start [-d <device-id>] -a <ability-name> -b <bundle-name> [-D]'
1654             // 'aa stop-service [-d <device-id>] -a <ability-name> -b <bundle-name>'
1655             HILOG_INFO("'aa %{public}s' without enough options.", cmd_.c_str());
1656 
1657             if (abilityName.size() == 0) {
1658                 resultReceiver_.append(HELP_MSG_NO_ABILITY_NAME_OPTION + "\n");
1659             }
1660 
1661             if (bundleName.size() == 0) {
1662                 resultReceiver_.append(HELP_MSG_NO_BUNDLE_NAME_OPTION + "\n");
1663             }
1664 
1665             result = OHOS::ERR_INVALID_VALUE;
1666         } else {
1667             ElementName element(deviceId, bundleName, abilityName, moduleName);
1668             want.SetElement(element);
1669 
1670             if (isColdStart) {
1671                 want.SetParam("coldStart", isColdStart);
1672             }
1673             if (isDebugApp) {
1674                 want.SetParam("debugApp", isDebugApp);
1675             }
1676             if (isContinuation) {
1677                 want.AddFlags(Want::FLAG_ABILITY_CONTINUATION);
1678             }
1679             if (!perfCmd.empty()) {
1680                 want.SetParam("perfCmd", perfCmd);
1681             }
1682             if (isSandboxApp) {
1683                 want.SetParam("sandboxApp", isSandboxApp);
1684             }
1685             if (isNativeDebug) {
1686                 want.SetParam("nativeDebug", isNativeDebug);
1687             }
1688             if (!parametersInteger.empty()) {
1689                 SetParams(parametersInteger, want);
1690             }
1691             if (!parametersBool.empty()) {
1692                 SetParams(parametersBool, want);
1693             }
1694             if (!parametersString.empty()) {
1695                 SetParams(parametersString, want);
1696             }
1697             if (!action.empty()) {
1698                 want.SetAction(action);
1699             }
1700             if (!uri.empty()) {
1701                 want.SetUri(uri);
1702             }
1703             if (!entities.empty()) {
1704                 AddEntities(entities, want);
1705             }
1706             if (!typeVal.empty()) {
1707                 want.SetType(typeVal);
1708             }
1709         }
1710     }
1711 
1712     return result;
1713 }
1714 
RunAsTestCommand()1715 ErrCode AbilityManagerShellCommand::RunAsTestCommand()
1716 {
1717     HILOG_INFO("enter");
1718     std::map<std::string, std::string> params;
1719 
1720     for (int i = USER_TEST_COMMAND_START_INDEX; i < argc_; i++) {
1721         HILOG_INFO("argv_[%{public}d]: %{public}s", i, argv_[i]);
1722         std::string opt = argv_[i];
1723         if ((opt == "-h") || (opt == "--help")) {
1724             resultReceiver_.append(HELP_MSG_TEST);
1725             return OHOS::ERR_OK;
1726         } else if ((opt == "-b") || (opt == "-p") || (opt == "-m")) {
1727             if (i >= argc_ - 1) {
1728                 return TestCommandError("error: option [" + opt + "] requires a value.\n");
1729             }
1730             std::string argv = argv_[++i];
1731             params[opt] = argv;
1732         } else if (opt == "-w") {
1733             if (i >= argc_ - 1) {
1734                 return TestCommandError("error: option [" + opt + "] requires a value.\n");
1735             }
1736 
1737             std::string argv = argv_[++i];
1738             std::smatch sm;
1739             auto isNumber = std::regex_match(argv, sm, std::regex(STRING_TEST_REGEX_INTEGER_NUMBERS));
1740             if (!isNumber) {
1741                 return TestCommandError("error: option [" + opt + "] only supports integer numbers.\n");
1742             }
1743 
1744             params[opt] = argv;
1745         } else if (opt == "-s") {
1746             if (i >= argc_ - USER_TEST_COMMAND_PARAMS_NUM) {
1747                 return TestCommandError("error: option [-s] is incorrect.\n");
1748             }
1749             std::string argKey = argv_[++i];
1750             std::string argValue = argv_[++i];
1751             params[opt + " " + argKey] = argValue;
1752         } else if (opt == "-D") {
1753             params[opt] = DEBUG_VALUE;
1754         } else if (opt.at(0) == '-') {
1755             return TestCommandError("error: unknown option: " + opt + "\n");
1756         }
1757     }
1758 
1759     if (!IsTestCommandIntegrity(params)) {
1760         return OHOS::ERR_INVALID_VALUE;
1761     }
1762 
1763     return StartUserTest(params);
1764 }
1765 
IsTestCommandIntegrity(const std::map<std::string,std::string> & params)1766 bool AbilityManagerShellCommand::IsTestCommandIntegrity(const std::map<std::string, std::string>& params)
1767 {
1768     HILOG_INFO("enter");
1769 
1770     std::vector<std::string> opts = { "-b", "-s unittest" };
1771     for (auto opt : opts) {
1772         auto it = params.find(opt);
1773         if (it == params.end()) {
1774             TestCommandError("error: the option [" + opt + "] is expected.\n");
1775             return false;
1776         }
1777     }
1778     return true;
1779 }
1780 
TestCommandError(const std::string & info)1781 ErrCode AbilityManagerShellCommand::TestCommandError(const std::string& info)
1782 {
1783     resultReceiver_.append(info);
1784     resultReceiver_.append(HELP_MSG_TEST);
1785     return OHOS::ERR_INVALID_VALUE;
1786 }
1787 
StartUserTest(const std::map<std::string,std::string> & params)1788 ErrCode AbilityManagerShellCommand::StartUserTest(const std::map<std::string, std::string>& params)
1789 {
1790     HILOG_INFO("enter");
1791 
1792     Want want;
1793     for (auto param : params) {
1794         want.SetParam(param.first, param.second);
1795     }
1796 
1797     auto dPos = params.find("-D");
1798     if (dPos != params.end() && dPos->second.compare(DEBUG_VALUE) == 0) {
1799         HILOG_INFO("Set Debug to want");
1800         want.SetParam("debugApp", true);
1801     }
1802 
1803     sptr<TestObserver> observer = new (std::nothrow) TestObserver();
1804     if (!observer) {
1805         HILOG_ERROR("Failed: the TestObserver is null");
1806         return OHOS::ERR_INVALID_VALUE;
1807     }
1808 
1809     int result = AbilityManagerClient::GetInstance()->StartUserTest(want, observer->AsObject());
1810     if (result != OHOS::ERR_OK) {
1811         HILOG_INFO("%{public}s result = %{public}d", STRING_START_USER_TEST_NG.c_str(), result);
1812         resultReceiver_ = STRING_START_USER_TEST_NG + "\n";
1813         resultReceiver_.append(GetMessageFromCode(result));
1814         return result;
1815     }
1816     HILOG_INFO("%{public}s", STRING_USER_TEST_STARTED.c_str());
1817 
1818     std::signal(SIGCHLD, SIG_DFL);
1819 
1820     int64_t timeMs = 0;
1821     if (!want.GetStringParam("-w").empty()) {
1822         auto time = std::stoi(want.GetStringParam("-w"));
1823         timeMs = time > 0 ? time * TIME_RATE_MS : 0;
1824     }
1825     if (!observer->WaitForFinish(timeMs)) {
1826         resultReceiver_ = "Timeout: user test is not completed within the specified time.\n";
1827         return OHOS::ERR_INVALID_VALUE;
1828     }
1829 
1830     HILOG_INFO("%{public}s", STRING_USER_TEST_FINISHED.c_str());
1831     resultReceiver_ = STRING_USER_TEST_FINISHED + "\n";
1832 
1833     return result;
1834 }
1835 
GetAbilityManagerService()1836 sptr<IAbilityManager> AbilityManagerShellCommand::GetAbilityManagerService()
1837 {
1838     sptr<ISystemAbilityManager> systemManager = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
1839     if (systemManager == nullptr) {
1840         HILOG_ERROR("Fail to get registry.");
1841         return nullptr;
1842     }
1843     sptr<IRemoteObject> remoteObject = systemManager->GetSystemAbility(ABILITY_MGR_SERVICE_ID);
1844     return iface_cast<IAbilityManager>(remoteObject);
1845 }
1846 
1847 #ifdef ABILITY_COMMAND_FOR_TEST
RunAsSendAppNotRespondingWithUnknownOption()1848 ErrCode AbilityManagerShellCommand::RunAsSendAppNotRespondingWithUnknownOption()
1849 {
1850     switch (optopt) {
1851         case 'h': {
1852             break;
1853         }
1854         case 'p': {
1855             HILOG_INFO("'aa ApplicationNotResponding -p' with no argument.");
1856             resultReceiver_.append("error: option -p ");
1857             resultReceiver_.append("' requires a value.\n");
1858             break;
1859         }
1860         default: {
1861             std::string unknownOption;
1862             std::string unknownOptionMsg = GetUnknownOptionMsg(unknownOption);
1863             HILOG_INFO("'aa ApplicationNotResponding' with an unknown option.");
1864             resultReceiver_.append(unknownOptionMsg);
1865             break;
1866         }
1867     }
1868     return OHOS::ERR_INVALID_VALUE;
1869 }
1870 
RunAsSendAppNotRespondingWithOption(int32_t option,std::string & pid)1871 ErrCode AbilityManagerShellCommand::RunAsSendAppNotRespondingWithOption(int32_t option, std::string& pid)
1872 {
1873     ErrCode result = ERR_OK;
1874     switch (option) {
1875         case 'h': {
1876             result = OHOS::ERR_INVALID_VALUE;
1877             break;
1878         }
1879         case 'p': {
1880             HILOG_INFO("aa ApplicationNotResponding 'aa %{public}s'  -p process.", cmd_.c_str());
1881             HILOG_INFO("aa ApplicationNotResponding 'aa optarg =  %{public}s'.", optarg);
1882             pid = optarg;
1883             HILOG_INFO("aa ApplicationNotResponding 'aa pid =  %{public}s'.", pid.c_str());
1884             break;
1885         }
1886         default: {
1887             HILOG_INFO("'aa %{public}s' with an unknown option.", cmd_.c_str());
1888             result = OHOS::ERR_INVALID_VALUE;
1889             break;
1890         }
1891     }
1892     return result;
1893 }
1894 
RunAsSendAppNotRespondingProcessID()1895 ErrCode AbilityManagerShellCommand::RunAsSendAppNotRespondingProcessID()
1896 {
1897     static sptr<IAbilityManager> abilityMs_;
1898     std::string pid = "";
1899     int option = -1;
1900     ErrCode result = OHOS::ERR_OK;
1901     option = getopt_long(argc_, argv_, SHORT_OPTIONS_APPLICATION_NOT_RESPONDING.c_str(),
1902         LONG_OPTIONS_ApplicationNotResponding, nullptr);
1903     HILOG_INFO("option: %{public}d, optopt: %{public}d, optind: %{public}d", option, optopt, optind);
1904     if (optind < 0 || optind > argc_) {
1905         return OHOS::ERR_INVALID_VALUE;
1906     }
1907     if (option == -1) {
1908         if (strcmp(argv_[optind], cmd_.c_str()) == 0) {
1909             HILOG_INFO("'aa %{public}s' %{public}s", HELP_ApplicationNotResponding.c_str(), cmd_.c_str());
1910             result = OHOS::ERR_INVALID_VALUE;
1911         }
1912     } else if (option == '?') {
1913         result = RunAsSendAppNotRespondingWithUnknownOption();
1914     } else {
1915         result = RunAsSendAppNotRespondingWithOption(option, pid);
1916     }
1917 
1918     if (result == OHOS::ERR_OK) {
1919         HILOG_INFO("'aa pid = %{public}d'.", atoi(pid.c_str()));
1920         abilityMs_ = GetAbilityManagerService();
1921         if (abilityMs_ == nullptr) {
1922             std::cout << "abilityMsObj is nullptr";
1923         } else {
1924             abilityMs_->SendANRProcessID(atoi(pid.c_str()));
1925         }
1926     } else {
1927         resultReceiver_.append(HELP_ApplicationNotResponding + "\n");
1928         result = OHOS::ERR_INVALID_VALUE;
1929     }
1930     return result;
1931 }
1932 
RunAsBlockAbilityCommand()1933 ErrCode AbilityManagerShellCommand::RunAsBlockAbilityCommand()
1934 {
1935     HILOG_INFO("[%{public}s(%{public}s)] enter", __FILE__, __FUNCTION__);
1936     ErrCode result = OHOS::ERR_OK;
1937     if (argList_.size() > 0) {
1938         result = AbilityManagerClient::GetInstance()->BlockAbility(atoi(argList_[0].c_str()));
1939     } else {
1940         result = OHOS::ERR_INVALID_VALUE;
1941     }
1942 
1943     if (result == OHOS::ERR_OK) {
1944         HILOG_INFO("%{public}s", STRING_BLOCK_ABILITY_OK.c_str());
1945         resultReceiver_ = STRING_BLOCK_ABILITY_OK + "\n";
1946     } else {
1947         HILOG_INFO("%{public}s result = %{public}d", STRING_BLOCK_ABILITY_NG.c_str(), result);
1948         resultReceiver_ = STRING_BLOCK_ABILITY_NG + "\n";
1949         resultReceiver_.append(GetMessageFromCode(result));
1950     }
1951     return result;
1952 }
1953 
RunAsBlockAmsServiceCommand()1954 ErrCode AbilityManagerShellCommand::RunAsBlockAmsServiceCommand()
1955 {
1956     HILOG_INFO("[%{public}s(%{public}s)] enter", __FILE__, __FUNCTION__);
1957     ErrCode result = OHOS::ERR_OK;
1958     result = AbilityManagerClient::GetInstance()->BlockAmsService();
1959     if (result == OHOS::ERR_OK) {
1960         HILOG_INFO("%{public}s", STRING_BLOCK_AMS_SERVICE_OK.c_str());
1961         resultReceiver_ = STRING_BLOCK_AMS_SERVICE_OK + "\n";
1962     } else {
1963         HILOG_INFO("%{public}s result = %{public}d", STRING_BLOCK_AMS_SERVICE_NG.c_str(), result);
1964         resultReceiver_ = STRING_BLOCK_AMS_SERVICE_NG + "\n";
1965         resultReceiver_.append(GetMessageFromCode(result));
1966     }
1967     return result;
1968 }
1969 
RunAsBlockAppServiceCommand()1970 ErrCode AbilityManagerShellCommand::RunAsBlockAppServiceCommand()
1971 {
1972     HILOG_INFO("[%{public}s(%{public}s)] enter", __FILE__, __FUNCTION__);
1973     ErrCode result = OHOS::ERR_OK;
1974     result = AbilityManagerClient::GetInstance()->BlockAppService();
1975     if (result == OHOS::ERR_OK) {
1976         HILOG_INFO("%{public}s", STRING_BLOCK_APP_SERVICE_OK.c_str());
1977         resultReceiver_ = STRING_BLOCK_APP_SERVICE_OK + "\n";
1978     } else {
1979         HILOG_INFO("%{public}s result = %{public}d", STRING_BLOCK_APP_SERVICE_NG.c_str(), result);
1980         resultReceiver_ = STRING_BLOCK_APP_SERVICE_NG + "\n";
1981         resultReceiver_.append(GetMessageFromCode(result));
1982     }
1983     return result;
1984 }
1985 #endif
1986 #ifdef ABILITY_FAULT_AND_EXIT_TEST
CovertExitReason(std::string & cmd)1987 Reason CovertExitReason(std::string &cmd)
1988 {
1989     if (cmd.empty()) {
1990         return Reason::REASON_UNKNOWN;
1991     }
1992 
1993     if (cmd.compare("UNKNOWN") == 0) {
1994         return Reason::REASON_UNKNOWN;
1995     } else if (cmd.compare("NORMAL") == 0) {
1996         return Reason::REASON_NORMAL;
1997     } else if (cmd.compare("CPP_CRASH") == 0) {
1998         return Reason::REASON_CPP_CRASH;
1999     } else if (cmd.compare("JS_ERROR") == 0) {
2000         return Reason::REASON_JS_ERROR;
2001     } else if (cmd.compare("ABILITY_NOT_RESPONDING") == 0) {
2002         return Reason::REASON_APP_FREEZE;
2003     } else if (cmd.compare("APP_FREEZE") == 0) {
2004         return Reason::REASON_APP_FREEZE;
2005     } else if (cmd.compare("PERFORMANCE_CONTROL") == 0) {
2006         return Reason::REASON_PERFORMANCE_CONTROL;
2007     } else if (cmd.compare("RESOURCE_CONTROL") == 0) {
2008         return Reason::REASON_RESOURCE_CONTROL;
2009     } else if (cmd.compare("UPGRADE") == 0) {
2010         return Reason::REASON_UPGRADE;
2011     }
2012 
2013     return Reason::REASON_UNKNOWN;
2014 }
2015 
RunAsForceExitAppCommand()2016 ErrCode AbilityManagerShellCommand::RunAsForceExitAppCommand()
2017 {
2018     HILOG_DEBUG("enter");
2019     int result = OHOS::ERR_OK;
2020 
2021     int option = -1;
2022     int counter = 0;
2023 
2024     std::string pid;
2025     std::string reason;
2026 
2027     while (true) {
2028         counter++;
2029         option = getopt_long(argc_, argv_, SHORT_OPTIONS_FORCE_EXIT_APP.c_str(), LONG_OPTIONS_FORCE_EXIT_APP, nullptr);
2030         HILOG_DEBUG("option: %{public}d, optopt: %{public}d, optind: %{public}d", option, optopt, optind);
2031 
2032         if (optind < 0 || optind > argc_) {
2033             return OHOS::ERR_INVALID_VALUE;
2034         }
2035 
2036         if (option == -1) {
2037             if (counter == 1 && strcmp(argv_[optind], cmd_.c_str()) == 0) {
2038                 HILOG_ERROR("'aa %{public}s' %{public}s", HELP_MSG_NO_OPTION.c_str(), cmd_.c_str());
2039                 resultReceiver_.append(HELP_MSG_NO_OPTION + "\n");
2040                 result = OHOS::ERR_INVALID_VALUE;
2041             }
2042             break;
2043         }
2044 
2045         switch (option) {
2046             case 'h': {
2047                 HILOG_INFO("'aa %{public}s -h' with no argument.", cmd_.c_str());
2048                 // 'aa forceexitapp -h'
2049                 // 'aa forceexitapp --help'
2050                 result = OHOS::ERR_INVALID_VALUE;
2051                 break;
2052             }
2053             case 'p': {
2054                 HILOG_INFO("'aa %{public}s -p' pid.", cmd_.c_str());
2055                 // 'aa forceexitapp -p pid'
2056                 pid = optarg;
2057                 break;
2058             }
2059             case 'r': {
2060                 HILOG_INFO("'aa %{public}s -r' reason.", cmd_.c_str());
2061                 // 'aa forceexitapp -r reason'
2062                 reason = optarg;
2063                 break;
2064             }
2065             case '?': {
2066                 std::string unknownOption = "";
2067                 std::string unknownOptionMsg = GetUnknownOptionMsg(unknownOption);
2068                 HILOG_INFO("'aa notifyappfault' with an unknown option.");
2069                 resultReceiver_.append(unknownOptionMsg);
2070                 result = OHOS::ERR_INVALID_VALUE;
2071                 break;
2072             }
2073             default: {
2074                 break;
2075             }
2076         }
2077     }
2078 
2079     if (result != OHOS::ERR_OK) {
2080         resultReceiver_.append(HELP_MSG_SCREEN);
2081         result = OHOS::ERR_INVALID_VALUE;
2082     }
2083 
2084     result = AbilityManagerClient::GetInstance()->ForceExitApp(std::stoi(pid), CovertExitReason(reason));
2085     if (result == OHOS::ERR_OK) {
2086         resultReceiver_ = STRING_BLOCK_AMS_SERVICE_OK + "\n";
2087     } else {
2088         HILOG_INFO("%{public}s result = %{public}d", STRING_BLOCK_AMS_SERVICE_NG.c_str(), result);
2089         resultReceiver_ = STRING_BLOCK_AMS_SERVICE_NG + "\n";
2090         resultReceiver_.append(GetMessageFromCode(result));
2091     }
2092 
2093     HILOG_DEBUG("pid: %{public}s, reason: %{public}s", pid.c_str(), reason.c_str());
2094     return result;
2095 }
2096 
CovertFaultType(std::string & cmd)2097 FaultDataType CovertFaultType(std::string &cmd)
2098 {
2099     if (cmd.empty()) {
2100         return FaultDataType::UNKNOWN;
2101     }
2102 
2103     if (cmd.compare("UNKNOWN") == 0) {
2104         return FaultDataType::UNKNOWN;
2105     } else if (cmd.compare("CPP_CRASH") == 0) {
2106         return FaultDataType::CPP_CRASH;
2107     } else if (cmd.compare("JS_ERROR") == 0) {
2108         return FaultDataType::JS_ERROR;
2109     } else if (cmd.compare("APP_FREEZE") == 0) {
2110         return FaultDataType::APP_FREEZE;
2111     } else if (cmd.compare("PERFORMANCE_CONTROL") == 0) {
2112         return FaultDataType::PERFORMANCE_CONTROL;
2113     } else if (cmd.compare("RESOURCE_CONTROL") == 0) {
2114         return FaultDataType::RESOURCE_CONTROL;
2115     }
2116 
2117     return FaultDataType::UNKNOWN;
2118 }
2119 
RunAsNotifyAppFaultCommand()2120 ErrCode AbilityManagerShellCommand::RunAsNotifyAppFaultCommand()
2121 {
2122     HILOG_DEBUG("called");
2123     int result = OHOS::ERR_OK;
2124     int option = -1;
2125     int counter = 0;
2126     std::string errorName = "";
2127     std::string errorMessage = "";
2128     std::string errorStack = "";
2129     std::string faultType = "";
2130     std::string pid = "";
2131     while (true) {
2132         counter++;
2133         option = getopt_long(
2134             argc_, argv_, SHORT_OPTIONS_NOTIFY_APP_FAULT.c_str(), LONG_OPTIONS_NOTIFY_APP_FAULT, nullptr);
2135         HILOG_INFO("option: %{public}d, optopt: %{public}d, optind: %{public}d", option, optopt, optind);
2136         if (optind < 0 || optind > argc_) {
2137             return OHOS::ERR_INVALID_VALUE;
2138         }
2139 
2140         if (option == -1) {
2141             if (counter == 1 && strcmp(argv_[optind], cmd_.c_str()) == 0) {
2142                 HILOG_INFO("'aa %{public}s' %{public}s", HELP_MSG_NO_OPTION.c_str(), cmd_.c_str());
2143                 resultReceiver_.append(HELP_MSG_NO_OPTION + "\n");
2144                 result = OHOS::ERR_INVALID_VALUE;
2145             }
2146             break;
2147         }
2148 
2149         switch (option) {
2150             case 'h': {
2151                 HILOG_INFO("'aa %{public}s -h' with no argument.", cmd_.c_str());
2152                 // 'aa notifyappfault -h'
2153                 // 'aa notifyappfault --help'
2154                 result = OHOS::ERR_INVALID_VALUE;
2155                 break;
2156             }
2157             case 'n': {
2158                 HILOG_INFO("'aa %{public}s -n' errorName.", cmd_.c_str());
2159                 // 'aa notifyappfault -n errorName'
2160                 errorName = optarg;
2161                 break;
2162             }
2163             case 'm': {
2164                 HILOG_INFO("'aa %{public}s -m' errorMessage.", cmd_.c_str());
2165                 // 'aa notifyappfault -m errorMessage'
2166                 errorMessage = optarg;
2167                 break;
2168             }
2169             case 's': {
2170                 HILOG_INFO("'aa %{public}s -s' errorStack.", cmd_.c_str());
2171                 // 'aa notifyappfault -s errorStack'
2172                 errorStack = optarg;
2173                 break;
2174             }
2175             case 't': {
2176                 HILOG_INFO("'aa %{public}s -t' faultType.", cmd_.c_str());
2177                 // 'aa notifyappfault -t faultType'
2178                 faultType = optarg;
2179                 break;
2180             }
2181             case 'p': {
2182                 HILOG_INFO("'aa %{public}s -p' pid.", cmd_.c_str());
2183                 // 'aa notifyappfault -p pid'
2184                 pid = optarg;
2185                 break;
2186             }
2187             case '?': {
2188                 std::string unknownOption = "";
2189                 std::string unknownOptionMsg = GetUnknownOptionMsg(unknownOption);
2190                 HILOG_INFO("'aa notifyappfault' with an unknown option.");
2191                 resultReceiver_.append(unknownOptionMsg);
2192                 result = OHOS::ERR_INVALID_VALUE;
2193                 break;
2194             }
2195             default: {
2196                 break;
2197             }
2198         }
2199     }
2200 
2201     if (result != OHOS::ERR_OK) {
2202         resultReceiver_.append(HELP_MSG_SCREEN);
2203         result = OHOS::ERR_INVALID_VALUE;
2204     }
2205 
2206     HILOG_INFO("name: %{public}s, message: %{public}s, stack: %{public}s, type: %{public}s, pid: %{public}s",
2207         errorName.c_str(), errorMessage.c_str(), errorStack.c_str(), faultType.c_str(), pid.c_str());
2208 
2209     AppFaultDataBySA faultData;
2210     faultData.errorObject.name = errorName;
2211     faultData.errorObject.message = errorMessage;
2212     faultData.errorObject.stack = errorStack;
2213     faultData.faultType = CovertFaultType(faultType);
2214     faultData.pid = std::stoi(pid);
2215     DelayedSingleton<AppMgrClient>::GetInstance()->NotifyAppFaultBySA(faultData);
2216     return result;
2217 }
2218 #endif
2219 }  // namespace AAFwk
2220 }  // namespace OHOS
2221