正在显示
7 个修改的文件
包含
509 行增加
和
13 行删除
| @@ -1079,6 +1079,18 @@ int SrsConfig::parse_options(int argc, char** argv) | @@ -1079,6 +1079,18 @@ int SrsConfig::parse_options(int argc, char** argv) | ||
| 1079 | { | 1079 | { |
| 1080 | int ret = ERROR_SUCCESS; | 1080 | int ret = ERROR_SUCCESS; |
| 1081 | 1081 | ||
| 1082 | + for (int i = 0; i < argc; i++) { | ||
| 1083 | + _argv.append(argv[i]); | ||
| 1084 | + | ||
| 1085 | + if (i < argc - 1) { | ||
| 1086 | + _argv.append(" "); | ||
| 1087 | + } | ||
| 1088 | + } | ||
| 1089 | + | ||
| 1090 | + char cwd[256]; | ||
| 1091 | + getcwd(cwd, sizeof(cwd)); | ||
| 1092 | + _cwd = cwd; | ||
| 1093 | + | ||
| 1082 | show_help = true; | 1094 | show_help = true; |
| 1083 | for (int i = 1; i < argc; i++) { | 1095 | for (int i = 1; i < argc; i++) { |
| 1084 | if ((ret = parse_argv(i, argv)) != ERROR_SUCCESS) { | 1096 | if ((ret = parse_argv(i, argv)) != ERROR_SUCCESS) { |
| @@ -1239,6 +1251,16 @@ void SrsConfig::print_help(char** argv) | @@ -1239,6 +1251,16 @@ void SrsConfig::print_help(char** argv) | ||
| 1239 | argv[0], argv[0], argv[0], argv[0]); | 1251 | argv[0], argv[0], argv[0], argv[0]); |
| 1240 | } | 1252 | } |
| 1241 | 1253 | ||
| 1254 | +string SrsConfig::get_cwd() | ||
| 1255 | +{ | ||
| 1256 | + return _cwd; | ||
| 1257 | +} | ||
| 1258 | + | ||
| 1259 | +string SrsConfig::get_argv() | ||
| 1260 | +{ | ||
| 1261 | + return _argv; | ||
| 1262 | +} | ||
| 1263 | + | ||
| 1242 | bool SrsConfig::get_deamon() | 1264 | bool SrsConfig::get_deamon() |
| 1243 | { | 1265 | { |
| 1244 | srs_assert(root); | 1266 | srs_assert(root); |
| @@ -120,6 +120,8 @@ private: | @@ -120,6 +120,8 @@ private: | ||
| 120 | bool test_conf; | 120 | bool test_conf; |
| 121 | bool show_version; | 121 | bool show_version; |
| 122 | std::string config_file; | 122 | std::string config_file; |
| 123 | + std::string _argv; | ||
| 124 | + std::string _cwd; | ||
| 123 | SrsConfDirective* root; | 125 | SrsConfDirective* root; |
| 124 | std::vector<ISrsReloadHandler*> subscribes; | 126 | std::vector<ISrsReloadHandler*> subscribes; |
| 125 | public: | 127 | public: |
| @@ -143,6 +145,9 @@ private: | @@ -143,6 +145,9 @@ private: | ||
| 143 | virtual int parse_file(const char* filename); | 145 | virtual int parse_file(const char* filename); |
| 144 | virtual int parse_argv(int& i, char** argv); | 146 | virtual int parse_argv(int& i, char** argv); |
| 145 | virtual void print_help(char** argv); | 147 | virtual void print_help(char** argv); |
| 148 | +public: | ||
| 149 | + virtual std::string get_cwd(); | ||
| 150 | + virtual std::string get_argv(); | ||
| 146 | // global section | 151 | // global section |
| 147 | public: | 152 | public: |
| 148 | virtual SrsConfDirective* get_root(); | 153 | virtual SrsConfDirective* get_root(); |
| @@ -34,6 +34,8 @@ using namespace std; | @@ -34,6 +34,8 @@ using namespace std; | ||
| 34 | #include <srs_app_socket.hpp> | 34 | #include <srs_app_socket.hpp> |
| 35 | #include <srs_core_autofree.hpp> | 35 | #include <srs_core_autofree.hpp> |
| 36 | #include <srs_app_json.hpp> | 36 | #include <srs_app_json.hpp> |
| 37 | +#include <srs_app_config.hpp> | ||
| 38 | +#include <srs_kernel_utility.hpp> | ||
| 37 | 39 | ||
| 38 | SrsApiRoot::SrsApiRoot() | 40 | SrsApiRoot::SrsApiRoot() |
| 39 | { | 41 | { |
| @@ -114,6 +116,8 @@ int SrsApiApi::do_process_request(SrsSocket* skt, SrsHttpMessage* req) | @@ -114,6 +116,8 @@ int SrsApiApi::do_process_request(SrsSocket* skt, SrsHttpMessage* req) | ||
| 114 | SrsApiV1::SrsApiV1() | 116 | SrsApiV1::SrsApiV1() |
| 115 | { | 117 | { |
| 116 | handlers.push_back(new SrsApiVersion()); | 118 | handlers.push_back(new SrsApiVersion()); |
| 119 | + handlers.push_back(new SrsApiSummaries()); | ||
| 120 | + handlers.push_back(new SrsApiRusages()); | ||
| 117 | handlers.push_back(new SrsApiAuthors()); | 121 | handlers.push_back(new SrsApiAuthors()); |
| 118 | } | 122 | } |
| 119 | 123 | ||
| @@ -134,6 +138,9 @@ int SrsApiV1::do_process_request(SrsSocket* skt, SrsHttpMessage* req) | @@ -134,6 +138,9 @@ int SrsApiV1::do_process_request(SrsSocket* skt, SrsHttpMessage* req) | ||
| 134 | << JFIELD_ERROR(ERROR_SUCCESS) << JFIELD_CONT | 138 | << JFIELD_ERROR(ERROR_SUCCESS) << JFIELD_CONT |
| 135 | << JFIELD_ORG("urls", JOBJECT_START) | 139 | << JFIELD_ORG("urls", JOBJECT_START) |
| 136 | << JFIELD_STR("versions", "the version of SRS") << JFIELD_CONT | 140 | << JFIELD_STR("versions", "the version of SRS") << JFIELD_CONT |
| 141 | + << JFIELD_STR("summaries", "the summary(pid, argv, pwd, cpu, mem) of SRS") << JFIELD_CONT | ||
| 142 | + << JFIELD_STR("rusages", "the rusage of SRS") << JFIELD_CONT | ||
| 143 | + << JFIELD_STR("proc_stats", "the /proc/self/stat of SRS") << JFIELD_CONT | ||
| 137 | << JFIELD_STR("authors", "the primary authors and contributors") | 144 | << JFIELD_STR("authors", "the primary authors and contributors") |
| 138 | << JOBJECT_END | 145 | << JOBJECT_END |
| 139 | << JOBJECT_END; | 146 | << JOBJECT_END; |
| @@ -171,6 +178,89 @@ int SrsApiVersion::do_process_request(SrsSocket* skt, SrsHttpMessage* req) | @@ -171,6 +178,89 @@ int SrsApiVersion::do_process_request(SrsSocket* skt, SrsHttpMessage* req) | ||
| 171 | return res_json(skt, req, ss.str()); | 178 | return res_json(skt, req, ss.str()); |
| 172 | } | 179 | } |
| 173 | 180 | ||
| 181 | +SrsApiSummaries::SrsApiSummaries() | ||
| 182 | +{ | ||
| 183 | +} | ||
| 184 | + | ||
| 185 | +SrsApiSummaries::~SrsApiSummaries() | ||
| 186 | +{ | ||
| 187 | +} | ||
| 188 | + | ||
| 189 | +bool SrsApiSummaries::can_handle(const char* path, int length, const char** /*pchild*/) | ||
| 190 | +{ | ||
| 191 | + return srs_path_equals("/summaries", path, length); | ||
| 192 | +} | ||
| 193 | + | ||
| 194 | +int SrsApiSummaries::do_process_request(SrsSocket* skt, SrsHttpMessage* req) | ||
| 195 | +{ | ||
| 196 | + std::stringstream ss; | ||
| 197 | + | ||
| 198 | + SrsRusage* r = srs_get_system_rusage(); | ||
| 199 | + SrsCpuSelfStat* u = srs_get_self_cpu_stat(); | ||
| 200 | + SrsCpuSystemStat* s = srs_get_system_cpu_stat(); | ||
| 201 | + | ||
| 202 | + ss << JOBJECT_START | ||
| 203 | + << JFIELD_ERROR(ERROR_SUCCESS) << JFIELD_CONT | ||
| 204 | + << JFIELD_ORG("data", JOBJECT_START) | ||
| 205 | + << JFIELD_ORG("pid", getpid()) << JFIELD_CONT | ||
| 206 | + << JFIELD_STR("argv", _srs_config->get_argv()) << JFIELD_CONT | ||
| 207 | + << JFIELD_STR("cwd", _srs_config->get_cwd()) << JFIELD_CONT | ||
| 208 | + << JFIELD_ORG("rusage_ok", (r->ok? "true":"false")) << JFIELD_CONT | ||
| 209 | + << JFIELD_ORG("self_cpu_stat_ok", (u->ok? "true":"false")) << JFIELD_CONT | ||
| 210 | + << JFIELD_ORG("system_cpu_stat_ok", (s->ok? "true":"false")) << JFIELD_CONT | ||
| 211 | + << JFIELD_ORG("mem_kbyte", r->r.ru_maxrss) << JFIELD_CONT | ||
| 212 | + << JFIELD_ORG("ppid", u->ppid) | ||
| 213 | + << JOBJECT_END | ||
| 214 | + << JOBJECT_END; | ||
| 215 | + | ||
| 216 | + return res_json(skt, req, ss.str()); | ||
| 217 | +} | ||
| 218 | + | ||
| 219 | +SrsApiRusages::SrsApiRusages() | ||
| 220 | +{ | ||
| 221 | +} | ||
| 222 | + | ||
| 223 | +SrsApiRusages::~SrsApiRusages() | ||
| 224 | +{ | ||
| 225 | +} | ||
| 226 | + | ||
| 227 | +bool SrsApiRusages::can_handle(const char* path, int length, const char** /*pchild*/) | ||
| 228 | +{ | ||
| 229 | + return srs_path_equals("/rusages", path, length); | ||
| 230 | +} | ||
| 231 | + | ||
| 232 | +int SrsApiRusages::do_process_request(SrsSocket* skt, SrsHttpMessage* req) | ||
| 233 | +{ | ||
| 234 | + std::stringstream ss; | ||
| 235 | + | ||
| 236 | + SrsRusage* r = srs_get_system_rusage(); | ||
| 237 | + | ||
| 238 | + ss << JOBJECT_START | ||
| 239 | + << JFIELD_ERROR(ERROR_SUCCESS) << JFIELD_CONT | ||
| 240 | + << JFIELD_ORG("data", JOBJECT_START) | ||
| 241 | + << JFIELD_ORG("rusage_ok", (r->ok? "true":"false")) << JFIELD_CONT | ||
| 242 | + << JFIELD_ORG("ru_utime", r->r.ru_utime.tv_sec) << JFIELD_CONT | ||
| 243 | + << JFIELD_ORG("ru_stime", r->r.ru_stime.tv_sec) << JFIELD_CONT | ||
| 244 | + << JFIELD_ORG("ru_maxrss", r->r.ru_maxrss) << JFIELD_CONT | ||
| 245 | + << JFIELD_ORG("ru_ixrss", r->r.ru_ixrss) << JFIELD_CONT | ||
| 246 | + << JFIELD_ORG("ru_idrss", r->r.ru_idrss) << JFIELD_CONT | ||
| 247 | + << JFIELD_ORG("ru_isrss", r->r.ru_isrss) << JFIELD_CONT | ||
| 248 | + << JFIELD_ORG("ru_minflt", r->r.ru_minflt) << JFIELD_CONT | ||
| 249 | + << JFIELD_ORG("ru_majflt", r->r.ru_majflt) << JFIELD_CONT | ||
| 250 | + << JFIELD_ORG("ru_nswap", r->r.ru_nswap) << JFIELD_CONT | ||
| 251 | + << JFIELD_ORG("ru_inblock", r->r.ru_inblock) << JFIELD_CONT | ||
| 252 | + << JFIELD_ORG("ru_oublock", r->r.ru_oublock) << JFIELD_CONT | ||
| 253 | + << JFIELD_ORG("ru_msgsnd", r->r.ru_msgsnd) << JFIELD_CONT | ||
| 254 | + << JFIELD_ORG("ru_msgrcv", r->r.ru_msgrcv) << JFIELD_CONT | ||
| 255 | + << JFIELD_ORG("ru_nsignals", r->r.ru_nsignals) << JFIELD_CONT | ||
| 256 | + << JFIELD_ORG("ru_nvcsw", r->r.ru_nvcsw) << JFIELD_CONT | ||
| 257 | + << JFIELD_ORG("ru_nivcsw", r->r.ru_nivcsw) | ||
| 258 | + << JOBJECT_END | ||
| 259 | + << JOBJECT_END; | ||
| 260 | + | ||
| 261 | + return res_json(skt, req, ss.str()); | ||
| 262 | +} | ||
| 263 | + | ||
| 174 | SrsApiAuthors::SrsApiAuthors() | 264 | SrsApiAuthors::SrsApiAuthors() |
| 175 | { | 265 | { |
| 176 | } | 266 | } |
| @@ -87,6 +87,28 @@ protected: | @@ -87,6 +87,28 @@ protected: | ||
| 87 | virtual int do_process_request(SrsSocket* skt, SrsHttpMessage* req); | 87 | virtual int do_process_request(SrsSocket* skt, SrsHttpMessage* req); |
| 88 | }; | 88 | }; |
| 89 | 89 | ||
| 90 | +class SrsApiSummaries : public SrsHttpHandler | ||
| 91 | +{ | ||
| 92 | +public: | ||
| 93 | + SrsApiSummaries(); | ||
| 94 | + virtual ~SrsApiSummaries(); | ||
| 95 | +public: | ||
| 96 | + virtual bool can_handle(const char* path, int length, const char** pchild); | ||
| 97 | +protected: | ||
| 98 | + virtual int do_process_request(SrsSocket* skt, SrsHttpMessage* req); | ||
| 99 | +}; | ||
| 100 | + | ||
| 101 | +class SrsApiRusages : public SrsHttpHandler | ||
| 102 | +{ | ||
| 103 | +public: | ||
| 104 | + SrsApiRusages(); | ||
| 105 | + virtual ~SrsApiRusages(); | ||
| 106 | +public: | ||
| 107 | + virtual bool can_handle(const char* path, int length, const char** pchild); | ||
| 108 | +protected: | ||
| 109 | + virtual int do_process_request(SrsSocket* skt, SrsHttpMessage* req); | ||
| 110 | +}; | ||
| 111 | + | ||
| 90 | class SrsApiAuthors : public SrsHttpHandler | 112 | class SrsApiAuthors : public SrsHttpHandler |
| 91 | { | 113 | { |
| 92 | public: | 114 | public: |
| @@ -46,7 +46,21 @@ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. | @@ -46,7 +46,21 @@ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. | ||
| 46 | #endif | 46 | #endif |
| 47 | 47 | ||
| 48 | #define SERVER_LISTEN_BACKLOG 512 | 48 | #define SERVER_LISTEN_BACKLOG 512 |
| 49 | -#define SRS_SYS_TIME_RESOLUTION_MS 500 | 49 | + |
| 50 | +// system interval | ||
| 51 | +#define SRS_SYS_CYCLE_INTERVAL 100 | ||
| 52 | + | ||
| 53 | +// update time interval: | ||
| 54 | +// SRS_SYS_CYCLE_INTERVAL * SRS_SYS_TIME_RESOLUTION_MS_TIMES | ||
| 55 | +#define SRS_SYS_TIME_RESOLUTION_MS_TIMES 3 | ||
| 56 | + | ||
| 57 | +// update rusage interval: | ||
| 58 | +// SRS_SYS_CYCLE_INTERVAL * SRS_SYS_RUSAGE_RESOLUTION_TIMES | ||
| 59 | +#define SRS_SYS_RUSAGE_RESOLUTION_TIMES 15 | ||
| 60 | + | ||
| 61 | +// update rusage interval: | ||
| 62 | +// SRS_SYS_CYCLE_INTERVAL * SRS_SYS_CPU_STAT_RESOLUTION_TIMES | ||
| 63 | +#define SRS_SYS_CPU_STAT_RESOLUTION_TIMES 15 | ||
| 50 | 64 | ||
| 51 | SrsListener::SrsListener(SrsServer* server, SrsListenerType type) | 65 | SrsListener::SrsListener(SrsServer* server, SrsListenerType type) |
| 52 | { | 66 | { |
| @@ -393,10 +407,15 @@ int SrsServer::cycle() | @@ -393,10 +407,15 @@ int SrsServer::cycle() | ||
| 393 | { | 407 | { |
| 394 | int ret = ERROR_SUCCESS; | 408 | int ret = ERROR_SUCCESS; |
| 395 | 409 | ||
| 410 | + // find the max loop | ||
| 411 | + int max = srs_max(0, SRS_SYS_TIME_RESOLUTION_MS_TIMES); | ||
| 412 | + max = srs_max(max, SRS_SYS_RUSAGE_RESOLUTION_TIMES); | ||
| 413 | + max = srs_max(max, SRS_SYS_CPU_STAT_RESOLUTION_TIMES); | ||
| 414 | + | ||
| 396 | // the deamon thread, update the time cache | 415 | // the deamon thread, update the time cache |
| 397 | while (true) { | 416 | while (true) { |
| 398 | - st_usleep(SRS_SYS_TIME_RESOLUTION_MS * 1000); | ||
| 399 | - srs_update_system_time_ms(); | 417 | + for (int i = 1; i < max + 1; i++) { |
| 418 | + st_usleep(SRS_SYS_CYCLE_INTERVAL * 1000); | ||
| 400 | 419 | ||
| 401 | // for gperf heap checker, | 420 | // for gperf heap checker, |
| 402 | // @see: research/gperftools/heap-checker/heap_checker.cc | 421 | // @see: research/gperftools/heap-checker/heap_checker.cc |
| @@ -404,20 +423,32 @@ int SrsServer::cycle() | @@ -404,20 +423,32 @@ int SrsServer::cycle() | ||
| 404 | // but, if gperf, use reload to ensure main return normally, | 423 | // but, if gperf, use reload to ensure main return normally, |
| 405 | // because directly exit will cause core-dump. | 424 | // because directly exit will cause core-dump. |
| 406 | #ifdef SRS_AUTO_GPERF_MC | 425 | #ifdef SRS_AUTO_GPERF_MC |
| 407 | - if (signal_gmc_stop) { | ||
| 408 | - break; | ||
| 409 | - } | 426 | + if (signal_gmc_stop) { |
| 427 | + break; | ||
| 428 | + } | ||
| 410 | #endif | 429 | #endif |
| 411 | 430 | ||
| 412 | - if (signal_reload) { | ||
| 413 | - signal_reload = false; | ||
| 414 | - srs_info("get signal reload, to reload the config."); | 431 | + if (signal_reload) { |
| 432 | + signal_reload = false; | ||
| 433 | + srs_info("get signal reload, to reload the config."); | ||
| 434 | + | ||
| 435 | + if ((ret = _srs_config->reload()) != ERROR_SUCCESS) { | ||
| 436 | + srs_error("reload config failed. ret=%d", ret); | ||
| 437 | + return ret; | ||
| 438 | + } | ||
| 439 | + srs_trace("reload config success."); | ||
| 440 | + } | ||
| 415 | 441 | ||
| 416 | - if ((ret = _srs_config->reload()) != ERROR_SUCCESS) { | ||
| 417 | - srs_error("reload config failed. ret=%d", ret); | ||
| 418 | - return ret; | 442 | + // update the cache time or rusage. |
| 443 | + if (i == SRS_SYS_TIME_RESOLUTION_MS_TIMES) { | ||
| 444 | + srs_update_system_time_ms(); | ||
| 445 | + } | ||
| 446 | + if (i == SRS_SYS_RUSAGE_RESOLUTION_TIMES) { | ||
| 447 | + srs_update_system_rusage(); | ||
| 448 | + } | ||
| 449 | + if (i == SRS_SYS_CPU_STAT_RESOLUTION_TIMES) { | ||
| 450 | + srs_update_system_cpu_stat(); | ||
| 419 | } | 451 | } |
| 420 | - srs_trace("reload config success."); | ||
| 421 | } | 452 | } |
| 422 | } | 453 | } |
| 423 | 454 |
| @@ -57,3 +57,116 @@ void srs_update_system_time_ms() | @@ -57,3 +57,116 @@ void srs_update_system_time_ms() | ||
| 57 | 57 | ||
| 58 | _srs_system_time_us_cache = now_us; | 58 | _srs_system_time_us_cache = now_us; |
| 59 | } | 59 | } |
| 60 | + | ||
| 61 | +static SrsRusage _srs_system_rusage; | ||
| 62 | + | ||
| 63 | +SrsRusage::SrsRusage() | ||
| 64 | +{ | ||
| 65 | + ok = false; | ||
| 66 | + memset(&r, 0, sizeof(rusage)); | ||
| 67 | +} | ||
| 68 | + | ||
| 69 | +SrsRusage* srs_get_system_rusage() | ||
| 70 | +{ | ||
| 71 | + return &_srs_system_rusage; | ||
| 72 | +} | ||
| 73 | + | ||
| 74 | +void srs_update_system_rusage() | ||
| 75 | +{ | ||
| 76 | + if (getrusage(RUSAGE_SELF, &_srs_system_rusage.r) < 0) { | ||
| 77 | + srs_warn("getrusage failed, ignore"); | ||
| 78 | + return; | ||
| 79 | + } | ||
| 80 | + | ||
| 81 | + _srs_system_rusage.ok = true; | ||
| 82 | +} | ||
| 83 | + | ||
| 84 | +static SrsCpuSelfStat _srs_system_cpu_self_stat; | ||
| 85 | +static SrsCpuSystemStat _srs_system_cpu_system_stat; | ||
| 86 | + | ||
| 87 | +SrsCpuSelfStat::SrsCpuSelfStat() | ||
| 88 | +{ | ||
| 89 | + ok = false; | ||
| 90 | +} | ||
| 91 | + | ||
| 92 | +SrsCpuSystemStat::SrsCpuSystemStat() | ||
| 93 | +{ | ||
| 94 | + ok = false; | ||
| 95 | +} | ||
| 96 | + | ||
| 97 | +SrsCpuSelfStat* srs_get_self_cpu_stat() | ||
| 98 | +{ | ||
| 99 | + return &_srs_system_cpu_self_stat; | ||
| 100 | +} | ||
| 101 | + | ||
| 102 | +SrsCpuSystemStat* srs_get_system_cpu_stat() | ||
| 103 | +{ | ||
| 104 | + return &_srs_system_cpu_system_stat; | ||
| 105 | +} | ||
| 106 | + | ||
| 107 | +void srs_update_system_cpu_stat() | ||
| 108 | +{ | ||
| 109 | + // system cpu stat | ||
| 110 | + if (true) { | ||
| 111 | + FILE* f = fopen("/proc/stat", "r"); | ||
| 112 | + if (f == NULL) { | ||
| 113 | + srs_warn("open system cpu stat failed, ignore"); | ||
| 114 | + return; | ||
| 115 | + } | ||
| 116 | + | ||
| 117 | + SrsCpuSystemStat& r = _srs_system_cpu_system_stat; | ||
| 118 | + for (;;) { | ||
| 119 | + int ret = fscanf(f, "%4s %lu %lu %lu %lu %lu " | ||
| 120 | + "%lu %lu %lu %lu\n", | ||
| 121 | + r.label, &r.user, &r.nice, &r.sys, &r.idle, &r.iowait, | ||
| 122 | + &r.irq, &r.softirq, &r.steal, &r.guest); | ||
| 123 | + r.ok = false; | ||
| 124 | + | ||
| 125 | + if (ret == EOF) { | ||
| 126 | + break; | ||
| 127 | + } | ||
| 128 | + | ||
| 129 | + if (strcmp("cpu", r.label) == 0) { | ||
| 130 | + r.ok = true; | ||
| 131 | + break; | ||
| 132 | + } | ||
| 133 | + } | ||
| 134 | + | ||
| 135 | + fclose(f); | ||
| 136 | + } | ||
| 137 | + | ||
| 138 | + // self cpu stat | ||
| 139 | + if (true) { | ||
| 140 | + FILE* f = fopen("/proc/self/stat", "r"); | ||
| 141 | + if (f == NULL) { | ||
| 142 | + srs_warn("open self cpu stat failed, ignore"); | ||
| 143 | + return; | ||
| 144 | + } | ||
| 145 | + | ||
| 146 | + SrsCpuSelfStat& r = _srs_system_cpu_self_stat; | ||
| 147 | + int ret = fscanf(f, "%d %32s %c %d %d %d %d " | ||
| 148 | + "%d %u %lu %lu %lu %lu " | ||
| 149 | + "%lu %lu %ld %ld %ld %ld " | ||
| 150 | + "%ld %ld %llu %lu %ld " | ||
| 151 | + "%lu %lu %lu %lu %lu " | ||
| 152 | + "%lu %lu %lu %lu %lu " | ||
| 153 | + "%lu %lu %lu %d %d " | ||
| 154 | + "%u %u %llu " | ||
| 155 | + "%lu %ld", | ||
| 156 | + &r.pid, r.comm, &r.state, &r.ppid, &r.pgrp, &r.session, &r.tty_nr, | ||
| 157 | + &r.tpgid, &r.flags, &r.minflt, &r.cminflt, &r.majflt, &r.cmajflt, | ||
| 158 | + &r.utime, &r.stime, &r.cutime, &r.cstime, &r.priority, &r.nice, | ||
| 159 | + &r.num_threads, &r.itrealvalue, &r.starttime, &r.vsize, &r.rss, | ||
| 160 | + &r.rsslim, &r.startcode, &r.endcode, &r.startstack, &r.kstkesp, | ||
| 161 | + &r.kstkeip, &r.signal, &r.blocked, &r.sigignore, &r.sigcatch, | ||
| 162 | + &r.wchan, &r.nswap, &r.cnswap, &r.exit_signal, &r.processor, | ||
| 163 | + &r.rt_priority, &r.policy, &r.delayacct_blkio_ticks, | ||
| 164 | + &r.guest_time, &r.cguest_time); | ||
| 165 | + | ||
| 166 | + if (ret >= 0) { | ||
| 167 | + r.ok = true; | ||
| 168 | + } | ||
| 169 | + | ||
| 170 | + fclose(f); | ||
| 171 | + } | ||
| 172 | +} |
| @@ -30,9 +30,222 @@ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. | @@ -30,9 +30,222 @@ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. | ||
| 30 | 30 | ||
| 31 | #include <srs_core.hpp> | 31 | #include <srs_core.hpp> |
| 32 | 32 | ||
| 33 | +#include <sys/resource.h> | ||
| 34 | + | ||
| 33 | // get current system time in ms, use cache to avoid performance problem | 35 | // get current system time in ms, use cache to avoid performance problem |
| 34 | extern int64_t srs_get_system_time_ms(); | 36 | extern int64_t srs_get_system_time_ms(); |
| 35 | // the deamon st-thread will update it. | 37 | // the deamon st-thread will update it. |
| 36 | extern void srs_update_system_time_ms(); | 38 | extern void srs_update_system_time_ms(); |
| 37 | 39 | ||
| 40 | +// @see: man getrusage | ||
| 41 | +struct SrsRusage | ||
| 42 | +{ | ||
| 43 | + bool ok; | ||
| 44 | + rusage r; | ||
| 45 | + | ||
| 46 | + SrsRusage(); | ||
| 47 | +}; | ||
| 48 | + | ||
| 49 | +// get system rusage, use cache to avoid performance problem. | ||
| 50 | +extern SrsRusage* srs_get_system_rusage(); | ||
| 51 | +// the deamon st-thread will update it. | ||
| 52 | +extern void srs_update_system_rusage(); | ||
| 53 | + | ||
| 54 | +// @see: man 5 proc, /proc/[pid]/stat | ||
| 55 | +struct SrsCpuSelfStat | ||
| 56 | +{ | ||
| 57 | + // whether the data is ok. | ||
| 58 | + bool ok; | ||
| 59 | + | ||
| 60 | + // pid %d The process ID. | ||
| 61 | + int pid; | ||
| 62 | + // comm %s The filename of the executable, in parentheses. This is visible whether or not the executable is | ||
| 63 | + // swapped out. | ||
| 64 | + char comm[32]; | ||
| 65 | + // state %c One character from the string "RSDZTW" where R is running, S is sleeping in an interruptible wait, D | ||
| 66 | + // is waiting in uninterruptible disk sleep, Z is zombie, T is traced or stopped (on a signal), and W is | ||
| 67 | + // paging. | ||
| 68 | + char state; | ||
| 69 | + // ppid %d The PID of the parent. | ||
| 70 | + int ppid; | ||
| 71 | + // pgrp %d The process group ID of the process. | ||
| 72 | + int pgrp; | ||
| 73 | + // session %d The session ID of the process. | ||
| 74 | + int session; | ||
| 75 | + // tty_nr %d The controlling terminal of the process. (The minor device number is contained in the combination of | ||
| 76 | + // bits 31 to 20 and 7 to 0; the major device number is in bits 15 t0 8.) | ||
| 77 | + int tty_nr; | ||
| 78 | + // tpgid %d The ID of the foreground process group of the controlling terminal of the process. | ||
| 79 | + int tpgid; | ||
| 80 | + // flags %u (%lu before Linux 2.6.22) | ||
| 81 | + // The kernel flags word of the process. For bit meanings, see the PF_* defines in <linux/sched.h>. | ||
| 82 | + // Details depend on the kernel version. | ||
| 83 | + unsigned int flags; | ||
| 84 | + // minflt %lu The number of minor faults the process has made which have not required loading a memory page from | ||
| 85 | + // disk. | ||
| 86 | + unsigned long minflt; | ||
| 87 | + // cminflt %lu The number of minor faults that the process’s waited-for children have made. | ||
| 88 | + unsigned long cminflt; | ||
| 89 | + // majflt %lu The number of major faults the process has made which have required loading a memory page from disk. | ||
| 90 | + unsigned long majflt; | ||
| 91 | + // cmajflt %lu The number of major faults that the process’s waited-for children have made. | ||
| 92 | + unsigned long cmajflt; | ||
| 93 | + // utime %lu Amount of time that this process has been scheduled in user mode, measured in clock ticks (divide by | ||
| 94 | + // sysconf(_SC_CLK_TCK). This includes guest time, guest_time (time spent running a virtual CPU, see | ||
| 95 | + // below), so that applications that are not aware of the guest time field do not lose that time from | ||
| 96 | + // their calculations. | ||
| 97 | + unsigned long utime; | ||
| 98 | + // stime %lu Amount of time that this process has been scheduled in kernel mode, measured in clock ticks (divide by | ||
| 99 | + // sysconf(_SC_CLK_TCK). | ||
| 100 | + unsigned long stime; | ||
| 101 | + // cutime %ld Amount of time that this process’s waited-for children have been scheduled in user mode, measured in | ||
| 102 | + // clock ticks (divide by sysconf(_SC_CLK_TCK). (See also times(2).) This includes guest time, | ||
| 103 | + // cguest_time (time spent running a virtual CPU, see below). | ||
| 104 | + long cutime; | ||
| 105 | + // cstime %ld Amount of time that this process’s waited-for children have been scheduled in kernel mode, measured in | ||
| 106 | + // clock ticks (divide by sysconf(_SC_CLK_TCK). | ||
| 107 | + long cstime; | ||
| 108 | + // priority %ld | ||
| 109 | + // (Explanation for Linux 2.6) For processes running a real-time scheduling policy (policy below; see | ||
| 110 | + // sched_setscheduler(2)), this is the negated scheduling priority, minus one; that is, a number in the | ||
| 111 | + // range -2 to -100, corresponding to real-time priorities 1 to 99. For processes running under a non- | ||
| 112 | + // real-time scheduling policy, this is the raw nice value (setpriority(2)) as represented in the kernel. | ||
| 113 | + // The kernel stores nice values as numbers in the range 0 (high) to 39 (low), corresponding to the user- | ||
| 114 | + // visible nice range of -20 to 19. | ||
| 115 | + // | ||
| 116 | + // Before Linux 2.6, this was a scaled value based on the scheduler weighting given to this process. | ||
| 117 | + long priority; | ||
| 118 | + // nice %ld The nice value (see setpriority(2)), a value in the range 19 (low priority) to -20 (high priority). | ||
| 119 | + long nice; | ||
| 120 | + // num_threads %ld | ||
| 121 | + // Number of threads in this process (since Linux 2.6). Before kernel 2.6, this field was hard coded to | ||
| 122 | + // 0 as a placeholder for an earlier removed field. | ||
| 123 | + long num_threads; | ||
| 124 | + // itrealvalue %ld | ||
| 125 | + // The time in jiffies before the next SIGALRM is sent to the process due to an interval timer. Since | ||
| 126 | + // kernel 2.6.17, this field is no longer maintained, and is hard coded as 0. | ||
| 127 | + long itrealvalue; | ||
| 128 | + // starttime %llu (was %lu before Linux 2.6) | ||
| 129 | + // The time in jiffies the process started after system boot. | ||
| 130 | + long long starttime; | ||
| 131 | + // vsize %lu Virtual memory size in bytes. | ||
| 132 | + unsigned long vsize; | ||
| 133 | + // rss %ld Resident Set Size: number of pages the process has in real memory. This is just the pages which count | ||
| 134 | + // towards text, data, or stack space. This does not include pages which have not been demand-loaded in, | ||
| 135 | + // or which are swapped out. | ||
| 136 | + long rss; | ||
| 137 | + // rsslim %lu Current soft limit in bytes on the rss of the process; see the description of RLIMIT_RSS in getprior- | ||
| 138 | + // ity(2). | ||
| 139 | + unsigned long rsslim; | ||
| 140 | + // startcode %lu | ||
| 141 | + // The address above which program text can run. | ||
| 142 | + unsigned long startcode; | ||
| 143 | + // endcode %lu The address below which program text can run. | ||
| 144 | + unsigned long endcode; | ||
| 145 | + // startstack %lu | ||
| 146 | + // The address of the start (i.e., bottom) of the stack. | ||
| 147 | + unsigned long startstack; | ||
| 148 | + // kstkesp %lu The current value of ESP (stack pointer), as found in the kernel stack page for the process. | ||
| 149 | + unsigned long kstkesp; | ||
| 150 | + // kstkeip %lu The current EIP (instruction pointer). | ||
| 151 | + unsigned long kstkeip; | ||
| 152 | + // signal %lu The bitmap of pending signals, displayed as a decimal number. Obsolete, because it does not provide | ||
| 153 | + // information on real-time signals; use /proc/[pid]/status instead. | ||
| 154 | + unsigned long signal; | ||
| 155 | + // blocked %lu The bitmap of blocked signals, displayed as a decimal number. Obsolete, because it does not provide | ||
| 156 | + // information on real-time signals; use /proc/[pid]/status instead. | ||
| 157 | + unsigned long blocked; | ||
| 158 | + // sigignore %lu | ||
| 159 | + // The bitmap of ignored signals, displayed as a decimal number. Obsolete, because it does not provide | ||
| 160 | + // information on real-time signals; use /proc/[pid]/status instead. | ||
| 161 | + unsigned long sigignore; | ||
| 162 | + // sigcatch %lu | ||
| 163 | + // The bitmap of caught signals, displayed as a decimal number. Obsolete, because it does not provide | ||
| 164 | + // information on real-time signals; use /proc/[pid]/status instead. | ||
| 165 | + unsigned long sigcatch; | ||
| 166 | + // wchan %lu This is the "channel" in which the process is waiting. It is the address of a system call, and can be | ||
| 167 | + // looked up in a namelist if you need a textual name. (If you have an up-to-date /etc/psdatabase, then | ||
| 168 | + // try ps -l to see the WCHAN field in action.) | ||
| 169 | + unsigned long wchan; | ||
| 170 | + // nswap %lu Number of pages swapped (not maintained). | ||
| 171 | + unsigned long nswap; | ||
| 172 | + // cnswap %lu Cumulative nswap for child processes (not maintained). | ||
| 173 | + unsigned long cnswap; | ||
| 174 | + // exit_signal %d (since Linux 2.1.22) | ||
| 175 | + // Signal to be sent to parent when we die. | ||
| 176 | + int exit_signal; | ||
| 177 | + // processor %d (since Linux 2.2.8) | ||
| 178 | + // CPU number last executed on. | ||
| 179 | + int processor; | ||
| 180 | + // rt_priority %u (since Linux 2.5.19; was %lu before Linux 2.6.22) | ||
| 181 | + // Real-time scheduling priority, a number in the range 1 to 99 for processes scheduled under a real-time | ||
| 182 | + // policy, or 0, for non-real-time processes (see sched_setscheduler(2)). | ||
| 183 | + unsigned int rt_priority; | ||
| 184 | + // policy %u (since Linux 2.5.19; was %lu before Linux 2.6.22) | ||
| 185 | + // Scheduling policy (see sched_setscheduler(2)). Decode using the SCHED_* constants in linux/sched.h. | ||
| 186 | + unsigned int policy; | ||
| 187 | + // delayacct_blkio_ticks %llu (since Linux 2.6.18) | ||
| 188 | + // Aggregated block I/O delays, measured in clock ticks (centiseconds). | ||
| 189 | + unsigned long long delayacct_blkio_ticks; | ||
| 190 | + // guest_time %lu (since Linux 2.6.24) | ||
| 191 | + // Guest time of the process (time spent running a virtual CPU for a guest operating system), measured in | ||
| 192 | + // clock ticks (divide by sysconf(_SC_CLK_TCK). | ||
| 193 | + unsigned long guest_time; | ||
| 194 | + // cguest_time %ld (since Linux 2.6.24) | ||
| 195 | + // Guest time of the process’s children, measured in clock ticks (divide by sysconf(_SC_CLK_TCK). | ||
| 196 | + long cguest_time; | ||
| 197 | + | ||
| 198 | + SrsCpuSelfStat(); | ||
| 199 | +}; | ||
| 200 | + | ||
| 201 | +// @see: man 5 proc, /proc/stat | ||
| 202 | +struct SrsCpuSystemStat | ||
| 203 | +{ | ||
| 204 | + // whether the data is ok. | ||
| 205 | + bool ok; | ||
| 206 | + | ||
| 207 | + // always be cpu | ||
| 208 | + char label[32]; | ||
| 209 | + | ||
| 210 | + //The amount of time, measured in units of USER_HZ (1/100ths of a second on most architectures, use | ||
| 211 | + // sysconf(_SC_CLK_TCK) to obtain the right value) | ||
| 212 | + // | ||
| 213 | + // the system spent in user mode, | ||
| 214 | + unsigned long user; | ||
| 215 | + // user mode with low priority (nice), | ||
| 216 | + unsigned long nice; | ||
| 217 | + // system mode, | ||
| 218 | + unsigned long sys; | ||
| 219 | + // and the idle task, respectively. | ||
| 220 | + unsigned long idle; | ||
| 221 | + | ||
| 222 | + // In Linux 2.6 this line includes three additional columns: | ||
| 223 | + // | ||
| 224 | + // iowait - time waiting for I/O to complete (since 2.5.41); | ||
| 225 | + unsigned long iowait; | ||
| 226 | + // irq - time servicing interrupts (since 2.6.0-test4); | ||
| 227 | + unsigned long irq; | ||
| 228 | + // softirq - time servicing softirqs (since 2.6.0-test4). | ||
| 229 | + unsigned long softirq; | ||
| 230 | + | ||
| 231 | + // Since Linux 2.6.11, there is an eighth column, | ||
| 232 | + // steal - stolen time, which is the time spent in other oper- | ||
| 233 | + // ating systems when running in a virtualized environment | ||
| 234 | + unsigned long steal; | ||
| 235 | + | ||
| 236 | + // Since Linux 2.6.24, there is a ninth column, | ||
| 237 | + // guest, which is the time spent running a virtual CPU for guest | ||
| 238 | + // operating systems under the control of the Linux kernel. | ||
| 239 | + unsigned long guest; | ||
| 240 | + | ||
| 241 | + SrsCpuSystemStat(); | ||
| 242 | +}; | ||
| 243 | + | ||
| 244 | +// get system cpu stat, use cache to avoid performance problem. | ||
| 245 | +extern SrsCpuSelfStat* srs_get_self_cpu_stat(); | ||
| 246 | +// get system cpu stat, use cache to avoid performance problem. | ||
| 247 | +extern SrsCpuSystemStat* srs_get_system_cpu_stat(); | ||
| 248 | +// the deamon st-thread will update it. | ||
| 249 | +extern void srs_update_system_cpu_stat(); | ||
| 250 | + | ||
| 38 | #endif | 251 | #endif |
-
请 注册 或 登录 后发表评论