1 /*
2  * Copyright (C) 2018 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 #pragma once
17 
18 #include <atomic>
19 #include <memory>
20 #include <mutex>
21 #include <set>
22 #include <string>
23 #include <utility>
24 #include <vector>
25 
26 #include "common/libs/utils/result.h"
27 #include "common/libs/utils/subprocess.h"
28 #include "host/libs/config/command_source.h"
29 
30 namespace cuttlefish {
31 
32 struct MonitorEntry {
33   std::unique_ptr<Command> cmd;
34   std::unique_ptr<Subprocess> proc;
35   bool is_critical;
36 
MonitorEntryMonitorEntry37   MonitorEntry(Command command, bool is_critical)
38       : cmd(new Command(std::move(command))), is_critical(is_critical) {}
39 };
40 
41 // Launches and keeps track of subprocesses, decides response if they
42 // unexpectedly exit
43 class ProcessMonitor {
44  public:
45   class Properties {
46    public:
47     Properties& RestartSubprocesses(bool) &;
48     Properties& AddCommand(MonitorCommand) &;
49     Properties& StraceCommands(std::set<std::string>) &;
50     Properties& StraceLogDir(std::string) &;
51 
52    private:
53     bool restart_subprocesses_;
54     std::vector<MonitorEntry> entries_;
55     std::set<std::string> strace_commands_;
56     std::string strace_log_dir_;
57 
58     friend class ProcessMonitor;
59   };
60   /*
61    * secure_env_fd is to send suspend/resume commands to secure_env.
62    */
63   ProcessMonitor(Properties&&, const SharedFD& secure_env_fd);
64 
65   // Start all processes given by AddCommand.
66   Result<void> StartAndMonitorProcesses();
67   // Stops all monitored subprocesses.
68   Result<void> StopMonitoredProcesses();
69   // Suspend all host subprocesses
70   Result<void> SuspendMonitoredProcesses();
71   // Resume all host subprocesses
72   Result<void> ResumeMonitoredProcesses();
73 
74  private:
75   Result<void> StartSubprocesses(Properties& properties);
76   Result<void> MonitorRoutine();
77   Result<void> ReadMonitorSocketLoop(std::atomic_bool&);
78   /*
79    * The child run_cvd process suspends the host processes
80    */
81   Result<void> SuspendHostProcessesImpl();
82   /*
83    * The child run_cvd process resumes the host processes
84    */
85   Result<void> ResumeHostProcessesImpl();
86 
87   Properties properties_;
88   const SharedFD channel_to_secure_env_;
89   pid_t monitor_;
90   SharedFD parent_monitor_socket_;
91   SharedFD child_monitor_socket_;
92 
93   /*
94    * The lock that should be acquired when multiple threads
95    * access to properties_. Currently, used by the child
96    * run_cvd process that runs MonitorRoutine()
97    */
98   std::mutex properties_mutex_;
99 };
100 
101 }  // namespace cuttlefish
102