1 // SPDX-License-Identifier: GPL-2.0 2 #include <internal/lib.h> 3 #include <inttypes.h> 4 #include <subcmd/parse-options.h> 5 #include <api/fd/array.h> 6 #include <api/fs/fs.h> 7 #include <linux/zalloc.h> 8 #include <linux/string.h> 9 #include <linux/limits.h> 10 #include <string.h> 11 #include <sys/file.h> 12 #include <signal.h> 13 #include <stdlib.h> 14 #include <time.h> 15 #include <stdio.h> 16 #include <unistd.h> 17 #include <errno.h> 18 #include <sys/inotify.h> 19 #include <libgen.h> 20 #include <sys/types.h> 21 #include <sys/socket.h> 22 #include <sys/un.h> 23 #include <sys/stat.h> 24 #include <sys/signalfd.h> 25 #include <sys/wait.h> 26 #include <poll.h> 27 #include "builtin.h" 28 #include "perf.h" 29 #include "debug.h" 30 #include "config.h" 31 #include "util.h" 32 33 #define SESSION_OUTPUT "output" 34 #define SESSION_CONTROL "control" 35 #define SESSION_ACK "ack" 36 37 /* 38 * Session states: 39 * 40 * OK - session is up and running 41 * RECONFIG - session is pending for reconfiguration, 42 * new values are already loaded in session object 43 * KILL - session is pending to be killed 44 * 45 * Session object life and its state is maintained by 46 * following functions: 47 * 48 * setup_server_config 49 * - reads config file and setup session objects 50 * with following states: 51 * 52 * OK - no change needed 53 * RECONFIG - session needs to be changed 54 * (run variable changed) 55 * KILL - session needs to be killed 56 * (session is no longer in config file) 57 * 58 * daemon__reconfig 59 * - scans session objects and does following actions 60 * for states: 61 * 62 * OK - skip 63 * RECONFIG - session is killed and re-run with new config 64 * KILL - session is killed 65 * 66 * - all sessions have OK state on the function exit 67 */ 68 enum daemon_session_state { 69 OK, 70 RECONFIG, 71 KILL, 72 }; 73 74 struct daemon_session { 75 char *base; 76 char *name; 77 char *run; 78 char *control; 79 int pid; 80 struct list_head list; 81 enum daemon_session_state state; 82 time_t start; 83 }; 84 85 struct daemon { 86 const char *config; 87 char *config_real; 88 char *config_base; 89 const char *csv_sep; 90 const char *base_user; 91 char *base; 92 struct list_head sessions; 93 FILE *out; 94 char *perf; 95 int signal_fd; 96 time_t start; 97 }; 98 99 static struct daemon __daemon = { 100 .sessions = LIST_HEAD_INIT(__daemon.sessions), 101 }; 102 103 static const char * const daemon_usage[] = { 104 "perf daemon {start|signal|stop|ping} [<options>]", 105 "perf daemon [<options>]", 106 NULL 107 }; 108 109 static volatile sig_atomic_t done; 110 111 static void sig_handler(int sig __maybe_unused) 112 { 113 done = true; 114 } 115 116 static struct daemon_session *daemon__add_session(struct daemon *config, char *name) 117 { 118 struct daemon_session *session = zalloc(sizeof(*session)); 119 120 if (!session) 121 return NULL; 122 123 session->name = strdup(name); 124 if (!session->name) { 125 free(session); 126 return NULL; 127 } 128 129 session->pid = -1; 130 list_add_tail(&session->list, &config->sessions); 131 return session; 132 } 133 134 static struct daemon_session *daemon__find_session(struct daemon *daemon, char *name) 135 { 136 struct daemon_session *session; 137 138 list_for_each_entry(session, &daemon->sessions, list) { 139 if (!strcmp(session->name, name)) 140 return session; 141 } 142 143 return NULL; 144 } 145 146 static int get_session_name(const char *var, char *session, int len) 147 { 148 const char *p = var + sizeof("session-") - 1; 149 150 while (*p != '.' && *p != 0x0 && len--) 151 *session++ = *p++; 152 153 *session = 0; 154 return *p == '.' ? 0 : -EINVAL; 155 } 156 157 static int session_config(struct daemon *daemon, const char *var, const char *value) 158 { 159 struct daemon_session *session; 160 char name[100]; 161 162 if (get_session_name(var, name, sizeof(name) - 1)) 163 return -EINVAL; 164 165 var = strchr(var, '.'); 166 if (!var) 167 return -EINVAL; 168 169 var++; 170 171 session = daemon__find_session(daemon, name); 172 173 if (!session) { 174 /* New session is defined. */ 175 session = daemon__add_session(daemon, name); 176 if (!session) 177 return -ENOMEM; 178 179 pr_debug("reconfig: found new session %s\n", name); 180 181 /* Trigger reconfig to start it. */ 182 session->state = RECONFIG; 183 } else if (session->state == KILL) { 184 /* Current session is defined, no action needed. */ 185 pr_debug("reconfig: found current session %s\n", name); 186 session->state = OK; 187 } 188 189 if (!strcmp(var, "run")) { 190 bool same = false; 191 192 if (session->run) 193 same = !strcmp(session->run, value); 194 195 if (!same) { 196 if (session->run) { 197 zfree(&session->run); 198 pr_debug("reconfig: session %s is changed\n", name); 199 } 200 201 session->run = strdup(value); 202 if (!session->run) 203 return -ENOMEM; 204 205 /* 206 * Either new or changed run value is defined, 207 * trigger reconfig for the session. 208 */ 209 session->state = RECONFIG; 210 } 211 } 212 213 return 0; 214 } 215 216 static int server_config(const char *var, const char *value, void *cb) 217 { 218 struct daemon *daemon = cb; 219 220 if (strstarts(var, "session-")) { 221 return session_config(daemon, var, value); 222 } else if (!strcmp(var, "daemon.base") && !daemon->base_user) { 223 if (daemon->base && strcmp(daemon->base, value)) { 224 pr_err("failed: can't redefine base, bailing out\n"); 225 return -EINVAL; 226 } 227 daemon->base = strdup(value); 228 if (!daemon->base) 229 return -ENOMEM; 230 } 231 232 return 0; 233 } 234 235 static int client_config(const char *var, const char *value, void *cb) 236 { 237 struct daemon *daemon = cb; 238 239 if (!strcmp(var, "daemon.base") && !daemon->base_user) { 240 daemon->base = strdup(value); 241 if (!daemon->base) 242 return -ENOMEM; 243 } 244 245 return 0; 246 } 247 248 static int check_base(struct daemon *daemon) 249 { 250 struct stat st; 251 252 if (!daemon->base) { 253 pr_err("failed: base not defined\n"); 254 return -EINVAL; 255 } 256 257 if (stat(daemon->base, &st)) { 258 switch (errno) { 259 case EACCES: 260 pr_err("failed: permission denied for '%s' base\n", 261 daemon->base); 262 return -EACCES; 263 case ENOENT: 264 pr_err("failed: base '%s' does not exists\n", 265 daemon->base); 266 return -EACCES; 267 default: 268 pr_err("failed: can't access base '%s': %s\n", 269 daemon->base, strerror(errno)); 270 return -errno; 271 } 272 } 273 274 if ((st.st_mode & S_IFMT) != S_IFDIR) { 275 pr_err("failed: base '%s' is not directory\n", 276 daemon->base); 277 return -EINVAL; 278 } 279 280 return 0; 281 } 282 283 static int setup_client_config(struct daemon *daemon) 284 { 285 struct perf_config_set *set = perf_config_set__load_file(daemon->config_real); 286 int err = -ENOMEM; 287 288 if (set) { 289 err = perf_config_set(set, client_config, daemon); 290 perf_config_set__delete(set); 291 } 292 293 return err ?: check_base(daemon); 294 } 295 296 static int setup_server_config(struct daemon *daemon) 297 { 298 struct perf_config_set *set; 299 struct daemon_session *session; 300 int err = -ENOMEM; 301 302 pr_debug("reconfig: started\n"); 303 304 /* 305 * Mark all sessions for kill, the server config 306 * will set following states, see explanation at 307 * enum daemon_session_state declaration. 308 */ 309 list_for_each_entry(session, &daemon->sessions, list) 310 session->state = KILL; 311 312 set = perf_config_set__load_file(daemon->config_real); 313 if (set) { 314 err = perf_config_set(set, server_config, daemon); 315 perf_config_set__delete(set); 316 } 317 318 return err ?: check_base(daemon); 319 } 320 321 static int daemon_session__run(struct daemon_session *session, 322 struct daemon *daemon) 323 { 324 char buf[PATH_MAX]; 325 char **argv; 326 int argc, fd; 327 328 if (asprintf(&session->base, "%s/session-%s", 329 daemon->base, session->name) < 0) { 330 perror("failed: asprintf"); 331 return -1; 332 } 333 334 if (mkdir(session->base, 0755) && errno != EEXIST) { 335 perror("failed: mkdir"); 336 return -1; 337 } 338 339 session->start = time(NULL); 340 341 session->pid = fork(); 342 if (session->pid < 0) 343 return -1; 344 if (session->pid > 0) { 345 pr_info("reconfig: ruining session [%s:%d]: %s\n", 346 session->name, session->pid, session->run); 347 return 0; 348 } 349 350 if (chdir(session->base)) { 351 perror("failed: chdir"); 352 return -1; 353 } 354 355 fd = open("/dev/null", O_RDONLY); 356 if (fd < 0) { 357 perror("failed: open /dev/null"); 358 return -1; 359 } 360 361 dup2(fd, 0); 362 close(fd); 363 364 fd = open(SESSION_OUTPUT, O_RDWR|O_CREAT|O_TRUNC, 0644); 365 if (fd < 0) { 366 perror("failed: open session output"); 367 return -1; 368 } 369 370 dup2(fd, 1); 371 dup2(fd, 2); 372 close(fd); 373 374 if (mkfifo(SESSION_CONTROL, 0600) && errno != EEXIST) { 375 perror("failed: create control fifo"); 376 return -1; 377 } 378 379 if (mkfifo(SESSION_ACK, 0600) && errno != EEXIST) { 380 perror("failed: create ack fifo"); 381 return -1; 382 } 383 384 scnprintf(buf, sizeof(buf), "%s record --control=fifo:%s,%s %s", 385 daemon->perf, SESSION_CONTROL, SESSION_ACK, session->run); 386 387 argv = argv_split(buf, &argc); 388 if (!argv) 389 exit(-1); 390 391 exit(execve(daemon->perf, argv, NULL)); 392 return -1; 393 } 394 395 static pid_t handle_signalfd(struct daemon *daemon) 396 { 397 struct daemon_session *session; 398 struct signalfd_siginfo si; 399 ssize_t err; 400 int status; 401 pid_t pid; 402 403 /* 404 * Take signal fd data as pure signal notification and check all 405 * the sessions state. The reason is that multiple signals can get 406 * coalesced in kernel and we can receive only single signal even 407 * if multiple SIGCHLD were generated. 408 */ 409 err = read(daemon->signal_fd, &si, sizeof(struct signalfd_siginfo)); 410 if (err != sizeof(struct signalfd_siginfo)) { 411 pr_err("failed to read signal fd\n"); 412 return -1; 413 } 414 415 list_for_each_entry(session, &daemon->sessions, list) { 416 if (session->pid == -1) 417 continue; 418 419 pid = waitpid(session->pid, &status, WNOHANG); 420 if (pid <= 0) 421 continue; 422 423 if (WIFEXITED(status)) { 424 pr_info("session '%s' exited, status=%d\n", 425 session->name, WEXITSTATUS(status)); 426 } else if (WIFSIGNALED(status)) { 427 pr_info("session '%s' killed (signal %d)\n", 428 session->name, WTERMSIG(status)); 429 } else if (WIFSTOPPED(status)) { 430 pr_info("session '%s' stopped (signal %d)\n", 431 session->name, WSTOPSIG(status)); 432 } else { 433 pr_info("session '%s' Unexpected status (0x%x)\n", 434 session->name, status); 435 } 436 437 session->state = KILL; 438 session->pid = -1; 439 } 440 441 return 0; 442 } 443 444 static int daemon_session__wait(struct daemon_session *session, struct daemon *daemon, 445 int secs) 446 { 447 struct pollfd pollfd = { 448 .fd = daemon->signal_fd, 449 .events = POLLIN, 450 }; 451 time_t start; 452 453 start = time(NULL); 454 455 do { 456 int err = poll(&pollfd, 1, 1000); 457 458 if (err > 0) { 459 handle_signalfd(daemon); 460 } else if (err < 0) { 461 perror("failed: poll\n"); 462 return -1; 463 } 464 465 if (start + secs < time(NULL)) 466 return -1; 467 } while (session->pid != -1); 468 469 return 0; 470 } 471 472 static bool daemon__has_alive_session(struct daemon *daemon) 473 { 474 struct daemon_session *session; 475 476 list_for_each_entry(session, &daemon->sessions, list) { 477 if (session->pid != -1) 478 return true; 479 } 480 481 return false; 482 } 483 484 static int daemon__wait(struct daemon *daemon, int secs) 485 { 486 struct pollfd pollfd = { 487 .fd = daemon->signal_fd, 488 .events = POLLIN, 489 }; 490 time_t start; 491 492 start = time(NULL); 493 494 do { 495 int err = poll(&pollfd, 1, 1000); 496 497 if (err > 0) { 498 handle_signalfd(daemon); 499 } else if (err < 0) { 500 perror("failed: poll\n"); 501 return -1; 502 } 503 504 if (start + secs < time(NULL)) 505 return -1; 506 } while (daemon__has_alive_session(daemon)); 507 508 return 0; 509 } 510 511 static int daemon_session__control(struct daemon_session *session, 512 const char *msg, bool do_ack) 513 { 514 struct pollfd pollfd = { .events = POLLIN, }; 515 char control_path[PATH_MAX]; 516 char ack_path[PATH_MAX]; 517 int control, ack = -1, len; 518 char buf[20]; 519 int ret = -1; 520 ssize_t err; 521 522 /* open the control file */ 523 scnprintf(control_path, sizeof(control_path), "%s/%s", 524 session->base, SESSION_CONTROL); 525 526 control = open(control_path, O_WRONLY|O_NONBLOCK); 527 if (control < 0) 528 return -1; 529 530 if (do_ack) { 531 /* open the ack file */ 532 scnprintf(ack_path, sizeof(ack_path), "%s/%s", 533 session->base, SESSION_ACK); 534 535 ack = open(ack_path, O_RDONLY, O_NONBLOCK); 536 if (ack < 0) { 537 close(control); 538 return -1; 539 } 540 } 541 542 /* write the command */ 543 len = strlen(msg); 544 545 err = writen(control, msg, len); 546 if (err != len) { 547 pr_err("failed: write to control pipe: %d (%s)\n", 548 errno, control_path); 549 goto out; 550 } 551 552 if (!do_ack) 553 goto out; 554 555 /* wait for an ack */ 556 pollfd.fd = ack; 557 558 if (!poll(&pollfd, 1, 2000)) { 559 pr_err("failed: control ack timeout\n"); 560 goto out; 561 } 562 563 if (!(pollfd.revents & POLLIN)) { 564 pr_err("failed: did not received an ack\n"); 565 goto out; 566 } 567 568 err = read(ack, buf, sizeof(buf)); 569 if (err > 0) 570 ret = strcmp(buf, "ack\n"); 571 else 572 perror("failed: read ack %d\n"); 573 574 out: 575 if (ack != -1) 576 close(ack); 577 578 close(control); 579 return ret; 580 } 581 582 static int setup_server_socket(struct daemon *daemon) 583 { 584 struct sockaddr_un addr; 585 char path[PATH_MAX]; 586 int fd = socket(AF_UNIX, SOCK_STREAM, 0); 587 588 if (fd < 0) { 589 fprintf(stderr, "socket: %s\n", strerror(errno)); 590 return -1; 591 } 592 593 if (fcntl(fd, F_SETFD, FD_CLOEXEC)) { 594 perror("failed: fcntl FD_CLOEXEC"); 595 close(fd); 596 return -1; 597 } 598 599 scnprintf(path, sizeof(path), "%s/control", daemon->base); 600 601 if (strlen(path) + 1 >= sizeof(addr.sun_path)) { 602 pr_err("failed: control path too long '%s'\n", path); 603 close(fd); 604 return -1; 605 } 606 607 memset(&addr, 0, sizeof(addr)); 608 addr.sun_family = AF_UNIX; 609 610 strlcpy(addr.sun_path, path, sizeof(addr.sun_path) - 1); 611 unlink(path); 612 613 if (bind(fd, (struct sockaddr *)&addr, sizeof(addr)) == -1) { 614 perror("failed: bind"); 615 close(fd); 616 return -1; 617 } 618 619 if (listen(fd, 1) == -1) { 620 perror("failed: listen"); 621 close(fd); 622 return -1; 623 } 624 625 return fd; 626 } 627 628 enum { 629 CMD_LIST = 0, 630 CMD_SIGNAL = 1, 631 CMD_STOP = 2, 632 CMD_PING = 3, 633 CMD_MAX, 634 }; 635 636 #define SESSION_MAX 64 637 638 union cmd { 639 int cmd; 640 641 /* CMD_LIST */ 642 struct { 643 int cmd; 644 int verbose; 645 char csv_sep; 646 } list; 647 648 /* CMD_SIGNAL */ 649 struct { 650 int cmd; 651 int sig; 652 char name[SESSION_MAX]; 653 } signal; 654 655 /* CMD_PING */ 656 struct { 657 int cmd; 658 char name[SESSION_MAX]; 659 } ping; 660 }; 661 662 enum { 663 PING_OK = 0, 664 PING_FAIL = 1, 665 PING_MAX, 666 }; 667 668 static int daemon_session__ping(struct daemon_session *session) 669 { 670 return daemon_session__control(session, "ping", true) ? PING_FAIL : PING_OK; 671 } 672 673 static int cmd_session_list(struct daemon *daemon, union cmd *cmd, FILE *out) 674 { 675 char csv_sep = cmd->list.csv_sep; 676 struct daemon_session *session; 677 time_t curr = time(NULL); 678 679 if (csv_sep) { 680 fprintf(out, "%d%c%s%c%s%c%s/%s", 681 /* pid daemon */ 682 getpid(), csv_sep, "daemon", 683 /* base */ 684 csv_sep, daemon->base, 685 /* output */ 686 csv_sep, daemon->base, SESSION_OUTPUT); 687 688 fprintf(out, "%c%s/%s", 689 /* lock */ 690 csv_sep, daemon->base, "lock"); 691 692 fprintf(out, "%c%" PRIu64, 693 /* session up time */ 694 csv_sep, (uint64_t)((curr - daemon->start) / 60)); 695 696 fprintf(out, "\n"); 697 } else { 698 fprintf(out, "[%d:daemon] base: %s\n", getpid(), daemon->base); 699 if (cmd->list.verbose) { 700 fprintf(out, " output: %s/%s\n", 701 daemon->base, SESSION_OUTPUT); 702 fprintf(out, " lock: %s/lock\n", 703 daemon->base); 704 fprintf(out, " up: %" PRIu64 " minutes\n", 705 (uint64_t)((curr - daemon->start) / 60)); 706 } 707 } 708 709 list_for_each_entry(session, &daemon->sessions, list) { 710 if (csv_sep) { 711 fprintf(out, "%d%c%s%c%s", 712 /* pid */ 713 session->pid, 714 /* name */ 715 csv_sep, session->name, 716 /* base */ 717 csv_sep, session->run); 718 719 fprintf(out, "%c%s%c%s/%s", 720 /* session dir */ 721 csv_sep, session->base, 722 /* session output */ 723 csv_sep, session->base, SESSION_OUTPUT); 724 725 fprintf(out, "%c%s/%s%c%s/%s", 726 /* session control */ 727 csv_sep, session->base, SESSION_CONTROL, 728 /* session ack */ 729 csv_sep, session->base, SESSION_ACK); 730 731 fprintf(out, "%c%" PRIu64, 732 /* session up time */ 733 csv_sep, (uint64_t)((curr - session->start) / 60)); 734 735 fprintf(out, "\n"); 736 } else { 737 fprintf(out, "[%d:%s] perf record %s\n", 738 session->pid, session->name, session->run); 739 if (!cmd->list.verbose) 740 continue; 741 fprintf(out, " base: %s\n", 742 session->base); 743 fprintf(out, " output: %s/%s\n", 744 session->base, SESSION_OUTPUT); 745 fprintf(out, " control: %s/%s\n", 746 session->base, SESSION_CONTROL); 747 fprintf(out, " ack: %s/%s\n", 748 session->base, SESSION_ACK); 749 fprintf(out, " up: %" PRIu64 " minutes\n", 750 (uint64_t)((curr - session->start) / 60)); 751 } 752 } 753 754 return 0; 755 } 756 757 static int daemon_session__signal(struct daemon_session *session, int sig) 758 { 759 if (session->pid < 0) 760 return -1; 761 return kill(session->pid, sig); 762 } 763 764 static int cmd_session_kill(struct daemon *daemon, union cmd *cmd, FILE *out) 765 { 766 struct daemon_session *session; 767 bool all = false; 768 769 all = !strcmp(cmd->signal.name, "all"); 770 771 list_for_each_entry(session, &daemon->sessions, list) { 772 if (all || !strcmp(cmd->signal.name, session->name)) { 773 daemon_session__signal(session, cmd->signal.sig); 774 fprintf(out, "signal %d sent to session '%s [%d]'\n", 775 cmd->signal.sig, session->name, session->pid); 776 } 777 } 778 779 return 0; 780 } 781 782 static const char *ping_str[PING_MAX] = { 783 [PING_OK] = "OK", 784 [PING_FAIL] = "FAIL", 785 }; 786 787 static int cmd_session_ping(struct daemon *daemon, union cmd *cmd, FILE *out) 788 { 789 struct daemon_session *session; 790 bool all = false, found = false; 791 792 all = !strcmp(cmd->ping.name, "all"); 793 794 list_for_each_entry(session, &daemon->sessions, list) { 795 if (all || !strcmp(cmd->ping.name, session->name)) { 796 int state = daemon_session__ping(session); 797 798 fprintf(out, "%-4s %s\n", ping_str[state], session->name); 799 found = true; 800 } 801 } 802 803 if (!found && !all) { 804 fprintf(out, "%-4s %s (not found)\n", 805 ping_str[PING_FAIL], cmd->ping.name); 806 } 807 return 0; 808 } 809 810 static int handle_server_socket(struct daemon *daemon, int sock_fd) 811 { 812 int ret = -1, fd; 813 FILE *out = NULL; 814 union cmd cmd; 815 816 fd = accept(sock_fd, NULL, NULL); 817 if (fd < 0) { 818 perror("failed: accept"); 819 return -1; 820 } 821 822 if (sizeof(cmd) != readn(fd, &cmd, sizeof(cmd))) { 823 perror("failed: read"); 824 goto out; 825 } 826 827 out = fdopen(fd, "w"); 828 if (!out) { 829 perror("failed: fdopen"); 830 goto out; 831 } 832 833 switch (cmd.cmd) { 834 case CMD_LIST: 835 ret = cmd_session_list(daemon, &cmd, out); 836 break; 837 case CMD_SIGNAL: 838 ret = cmd_session_kill(daemon, &cmd, out); 839 break; 840 case CMD_STOP: 841 done = 1; 842 ret = 0; 843 pr_debug("perf daemon is exciting\n"); 844 break; 845 case CMD_PING: 846 ret = cmd_session_ping(daemon, &cmd, out); 847 break; 848 default: 849 break; 850 } 851 852 fclose(out); 853 out: 854 /* If out is defined, then fd is closed via fclose. */ 855 if (!out) 856 close(fd); 857 return ret; 858 } 859 860 static int setup_client_socket(struct daemon *daemon) 861 { 862 struct sockaddr_un addr; 863 char path[PATH_MAX]; 864 int fd = socket(AF_UNIX, SOCK_STREAM, 0); 865 866 if (fd == -1) { 867 perror("failed: socket"); 868 return -1; 869 } 870 871 scnprintf(path, sizeof(path), "%s/control", daemon->base); 872 873 if (strlen(path) + 1 >= sizeof(addr.sun_path)) { 874 pr_err("failed: control path too long '%s'\n", path); 875 close(fd); 876 return -1; 877 } 878 879 memset(&addr, 0, sizeof(addr)); 880 addr.sun_family = AF_UNIX; 881 strlcpy(addr.sun_path, path, sizeof(addr.sun_path) - 1); 882 883 if (connect(fd, (struct sockaddr *) &addr, sizeof(addr)) == -1) { 884 perror("failed: connect"); 885 close(fd); 886 return -1; 887 } 888 889 return fd; 890 } 891 892 static void daemon_session__kill(struct daemon_session *session, 893 struct daemon *daemon) 894 { 895 int how = 0; 896 897 do { 898 switch (how) { 899 case 0: 900 daemon_session__control(session, "stop", false); 901 break; 902 case 1: 903 daemon_session__signal(session, SIGTERM); 904 break; 905 case 2: 906 daemon_session__signal(session, SIGKILL); 907 break; 908 default: 909 pr_err("failed to wait for session %s\n", 910 session->name); 911 return; 912 } 913 how++; 914 915 } while (daemon_session__wait(session, daemon, 10)); 916 } 917 918 static void daemon__signal(struct daemon *daemon, int sig) 919 { 920 struct daemon_session *session; 921 922 list_for_each_entry(session, &daemon->sessions, list) 923 daemon_session__signal(session, sig); 924 } 925 926 static void daemon_session__delete(struct daemon_session *session) 927 { 928 zfree(&session->base); 929 zfree(&session->name); 930 zfree(&session->run); 931 free(session); 932 } 933 934 static void daemon_session__remove(struct daemon_session *session) 935 { 936 list_del(&session->list); 937 daemon_session__delete(session); 938 } 939 940 static void daemon__stop(struct daemon *daemon) 941 { 942 struct daemon_session *session; 943 944 list_for_each_entry(session, &daemon->sessions, list) 945 daemon_session__control(session, "stop", false); 946 } 947 948 static void daemon__kill(struct daemon *daemon) 949 { 950 int how = 0; 951 952 do { 953 switch (how) { 954 case 0: 955 daemon__stop(daemon); 956 break; 957 case 1: 958 daemon__signal(daemon, SIGTERM); 959 break; 960 case 2: 961 daemon__signal(daemon, SIGKILL); 962 break; 963 default: 964 pr_err("failed to wait for sessions\n"); 965 return; 966 } 967 how++; 968 969 } while (daemon__wait(daemon, 10)); 970 } 971 972 static void daemon__exit(struct daemon *daemon) 973 { 974 struct daemon_session *session, *h; 975 976 list_for_each_entry_safe(session, h, &daemon->sessions, list) 977 daemon_session__remove(session); 978 979 zfree(&daemon->config_real); 980 zfree(&daemon->config_base); 981 zfree(&daemon->base); 982 } 983 984 static int daemon__reconfig(struct daemon *daemon) 985 { 986 struct daemon_session *session, *n; 987 988 list_for_each_entry_safe(session, n, &daemon->sessions, list) { 989 /* No change. */ 990 if (session->state == OK) 991 continue; 992 993 /* Remove session. */ 994 if (session->state == KILL) { 995 if (session->pid > 0) { 996 daemon_session__kill(session, daemon); 997 pr_info("reconfig: session '%s' killed\n", session->name); 998 } 999 daemon_session__remove(session); 1000 continue; 1001 } 1002 1003 /* Reconfig session. */ 1004 if (session->pid > 0) { 1005 daemon_session__kill(session, daemon); 1006 pr_info("reconfig: session '%s' killed\n", session->name); 1007 } 1008 if (daemon_session__run(session, daemon)) 1009 return -1; 1010 1011 session->state = OK; 1012 } 1013 1014 return 0; 1015 } 1016 1017 static int setup_config_changes(struct daemon *daemon) 1018 { 1019 char *basen = strdup(daemon->config_real); 1020 char *dirn = strdup(daemon->config_real); 1021 char *base, *dir; 1022 int fd, wd = -1; 1023 1024 if (!dirn || !basen) 1025 goto out; 1026 1027 fd = inotify_init1(IN_NONBLOCK|O_CLOEXEC); 1028 if (fd < 0) { 1029 perror("failed: inotify_init"); 1030 goto out; 1031 } 1032 1033 dir = dirname(dirn); 1034 base = basename(basen); 1035 pr_debug("config file: %s, dir: %s\n", base, dir); 1036 1037 wd = inotify_add_watch(fd, dir, IN_CLOSE_WRITE); 1038 if (wd >= 0) { 1039 daemon->config_base = strdup(base); 1040 if (!daemon->config_base) { 1041 close(fd); 1042 wd = -1; 1043 } 1044 } else { 1045 perror("failed: inotify_add_watch"); 1046 } 1047 1048 out: 1049 free(basen); 1050 free(dirn); 1051 return wd < 0 ? -1 : fd; 1052 } 1053 1054 static bool process_inotify_event(struct daemon *daemon, char *buf, ssize_t len) 1055 { 1056 char *p = buf; 1057 1058 while (p < (buf + len)) { 1059 struct inotify_event *event = (struct inotify_event *) p; 1060 1061 /* 1062 * We monitor config directory, check if our 1063 * config file was changes. 1064 */ 1065 if ((event->mask & IN_CLOSE_WRITE) && 1066 !(event->mask & IN_ISDIR)) { 1067 if (!strcmp(event->name, daemon->config_base)) 1068 return true; 1069 } 1070 p += sizeof(*event) + event->len; 1071 } 1072 return false; 1073 } 1074 1075 static int handle_config_changes(struct daemon *daemon, int conf_fd, 1076 bool *config_changed) 1077 { 1078 char buf[4096]; 1079 ssize_t len; 1080 1081 while (!(*config_changed)) { 1082 len = read(conf_fd, buf, sizeof(buf)); 1083 if (len == -1) { 1084 if (errno != EAGAIN) { 1085 perror("failed: read"); 1086 return -1; 1087 } 1088 return 0; 1089 } 1090 *config_changed = process_inotify_event(daemon, buf, len); 1091 } 1092 return 0; 1093 } 1094 1095 static int setup_config(struct daemon *daemon) 1096 { 1097 if (daemon->base_user) { 1098 daemon->base = strdup(daemon->base_user); 1099 if (!daemon->base) 1100 return -ENOMEM; 1101 } 1102 1103 if (daemon->config) { 1104 char *real = realpath(daemon->config, NULL); 1105 1106 if (!real) { 1107 perror("failed: realpath"); 1108 return -1; 1109 } 1110 daemon->config_real = real; 1111 return 0; 1112 } 1113 1114 if (perf_config_system() && !access(perf_etc_perfconfig(), R_OK)) 1115 daemon->config_real = strdup(perf_etc_perfconfig()); 1116 else if (perf_config_global() && perf_home_perfconfig()) 1117 daemon->config_real = strdup(perf_home_perfconfig()); 1118 1119 return daemon->config_real ? 0 : -1; 1120 } 1121 1122 #ifndef F_TLOCK 1123 #define F_TLOCK 2 1124 1125 static int lockf(int fd, int cmd, off_t len) 1126 { 1127 if (cmd != F_TLOCK || len != 0) 1128 return -1; 1129 1130 return flock(fd, LOCK_EX | LOCK_NB); 1131 } 1132 #endif // F_TLOCK 1133 1134 /* 1135 * Each daemon tries to create and lock BASE/lock file, 1136 * if it's successful we are sure we're the only daemon 1137 * running over the BASE. 1138 * 1139 * Once daemon is finished, file descriptor to lock file 1140 * is closed and lock is released. 1141 */ 1142 static int check_lock(struct daemon *daemon) 1143 { 1144 char path[PATH_MAX]; 1145 char buf[20]; 1146 int fd, pid; 1147 ssize_t len; 1148 1149 scnprintf(path, sizeof(path), "%s/lock", daemon->base); 1150 1151 fd = open(path, O_RDWR|O_CREAT|O_CLOEXEC, 0640); 1152 if (fd < 0) 1153 return -1; 1154 1155 if (lockf(fd, F_TLOCK, 0) < 0) { 1156 filename__read_int(path, &pid); 1157 fprintf(stderr, "failed: another perf daemon (pid %d) owns %s\n", 1158 pid, daemon->base); 1159 close(fd); 1160 return -1; 1161 } 1162 1163 scnprintf(buf, sizeof(buf), "%d", getpid()); 1164 len = strlen(buf); 1165 1166 if (write(fd, buf, len) != len) { 1167 perror("failed: write"); 1168 close(fd); 1169 return -1; 1170 } 1171 1172 if (ftruncate(fd, len)) { 1173 perror("failed: ftruncate"); 1174 close(fd); 1175 return -1; 1176 } 1177 1178 return 0; 1179 } 1180 1181 static int go_background(struct daemon *daemon) 1182 { 1183 int pid, fd; 1184 1185 pid = fork(); 1186 if (pid < 0) 1187 return -1; 1188 1189 if (pid > 0) 1190 return 1; 1191 1192 if (setsid() < 0) 1193 return -1; 1194 1195 if (check_lock(daemon)) 1196 return -1; 1197 1198 umask(0); 1199 1200 if (chdir(daemon->base)) { 1201 perror("failed: chdir"); 1202 return -1; 1203 } 1204 1205 fd = open("output", O_RDWR|O_CREAT|O_TRUNC, 0644); 1206 if (fd < 0) { 1207 perror("failed: open"); 1208 return -1; 1209 } 1210 1211 if (fcntl(fd, F_SETFD, FD_CLOEXEC)) { 1212 perror("failed: fcntl FD_CLOEXEC"); 1213 close(fd); 1214 return -1; 1215 } 1216 1217 close(0); 1218 dup2(fd, 1); 1219 dup2(fd, 2); 1220 close(fd); 1221 1222 daemon->out = fdopen(1, "w"); 1223 if (!daemon->out) { 1224 close(1); 1225 close(2); 1226 return -1; 1227 } 1228 1229 setbuf(daemon->out, NULL); 1230 return 0; 1231 } 1232 1233 static int setup_signalfd(struct daemon *daemon) 1234 { 1235 sigset_t mask; 1236 1237 sigemptyset(&mask); 1238 sigaddset(&mask, SIGCHLD); 1239 1240 if (sigprocmask(SIG_BLOCK, &mask, NULL) == -1) 1241 return -1; 1242 1243 daemon->signal_fd = signalfd(-1, &mask, SFD_NONBLOCK|SFD_CLOEXEC); 1244 return daemon->signal_fd; 1245 } 1246 1247 static int __cmd_start(struct daemon *daemon, struct option parent_options[], 1248 int argc, const char **argv) 1249 { 1250 bool foreground = false; 1251 struct option start_options[] = { 1252 OPT_BOOLEAN('f', "foreground", &foreground, "stay on console"), 1253 OPT_PARENT(parent_options), 1254 OPT_END() 1255 }; 1256 int sock_fd = -1, conf_fd = -1, signal_fd = -1; 1257 int sock_pos, file_pos, signal_pos; 1258 struct fdarray fda; 1259 int err = 0; 1260 1261 argc = parse_options(argc, argv, start_options, daemon_usage, 0); 1262 if (argc) 1263 usage_with_options(daemon_usage, start_options); 1264 1265 daemon->start = time(NULL); 1266 1267 if (setup_config(daemon)) { 1268 pr_err("failed: config not found\n"); 1269 return -1; 1270 } 1271 1272 if (setup_server_config(daemon)) 1273 return -1; 1274 1275 if (foreground && check_lock(daemon)) 1276 return -1; 1277 1278 if (!foreground) { 1279 err = go_background(daemon); 1280 if (err) { 1281 /* original process, exit normally */ 1282 if (err == 1) 1283 err = 0; 1284 daemon__exit(daemon); 1285 return err; 1286 } 1287 } 1288 1289 debug_set_file(daemon->out); 1290 debug_set_display_time(true); 1291 1292 pr_info("daemon started (pid %d)\n", getpid()); 1293 1294 fdarray__init(&fda, 3); 1295 1296 sock_fd = setup_server_socket(daemon); 1297 if (sock_fd < 0) 1298 goto out; 1299 1300 conf_fd = setup_config_changes(daemon); 1301 if (conf_fd < 0) 1302 goto out; 1303 1304 signal_fd = setup_signalfd(daemon); 1305 if (signal_fd < 0) 1306 goto out; 1307 1308 sock_pos = fdarray__add(&fda, sock_fd, POLLIN|POLLERR|POLLHUP, 0); 1309 if (sock_pos < 0) 1310 goto out; 1311 1312 file_pos = fdarray__add(&fda, conf_fd, POLLIN|POLLERR|POLLHUP, 0); 1313 if (file_pos < 0) 1314 goto out; 1315 1316 signal_pos = fdarray__add(&fda, signal_fd, POLLIN|POLLERR|POLLHUP, 0); 1317 if (signal_pos < 0) 1318 goto out; 1319 1320 signal(SIGINT, sig_handler); 1321 signal(SIGTERM, sig_handler); 1322 signal(SIGPIPE, SIG_IGN); 1323 1324 while (!done && !err) { 1325 err = daemon__reconfig(daemon); 1326 1327 if (!err && fdarray__poll(&fda, -1)) { 1328 bool reconfig = false; 1329 1330 if (fda.entries[sock_pos].revents & POLLIN) 1331 err = handle_server_socket(daemon, sock_fd); 1332 if (fda.entries[file_pos].revents & POLLIN) 1333 err = handle_config_changes(daemon, conf_fd, &reconfig); 1334 if (fda.entries[signal_pos].revents & POLLIN) 1335 err = handle_signalfd(daemon) < 0; 1336 1337 if (reconfig) 1338 err = setup_server_config(daemon); 1339 } 1340 } 1341 1342 out: 1343 fdarray__exit(&fda); 1344 1345 daemon__kill(daemon); 1346 daemon__exit(daemon); 1347 1348 if (sock_fd != -1) 1349 close(sock_fd); 1350 if (conf_fd != -1) 1351 close(conf_fd); 1352 if (signal_fd != -1) 1353 close(signal_fd); 1354 1355 pr_info("daemon exited\n"); 1356 fclose(daemon->out); 1357 return err; 1358 } 1359 1360 static int send_cmd(struct daemon *daemon, union cmd *cmd) 1361 { 1362 int ret = -1, fd; 1363 char *line = NULL; 1364 size_t len = 0; 1365 ssize_t nread; 1366 FILE *in = NULL; 1367 1368 if (setup_client_config(daemon)) 1369 return -1; 1370 1371 fd = setup_client_socket(daemon); 1372 if (fd < 0) 1373 return -1; 1374 1375 if (sizeof(*cmd) != writen(fd, cmd, sizeof(*cmd))) { 1376 perror("failed: write"); 1377 goto out; 1378 } 1379 1380 in = fdopen(fd, "r"); 1381 if (!in) { 1382 perror("failed: fdopen"); 1383 goto out; 1384 } 1385 1386 while ((nread = getline(&line, &len, in)) != -1) { 1387 if (fwrite(line, nread, 1, stdout) != 1) 1388 goto out_fclose; 1389 fflush(stdout); 1390 } 1391 1392 ret = 0; 1393 out_fclose: 1394 fclose(in); 1395 free(line); 1396 out: 1397 /* If in is defined, then fd is closed via fclose. */ 1398 if (!in) 1399 close(fd); 1400 return ret; 1401 } 1402 1403 static int send_cmd_list(struct daemon *daemon) 1404 { 1405 union cmd cmd; 1406 1407 memset(&cmd, 0, sizeof(cmd)); 1408 cmd.list.cmd = CMD_LIST; 1409 cmd.list.verbose = verbose; 1410 cmd.list.csv_sep = daemon->csv_sep ? *daemon->csv_sep : 0; 1411 1412 return send_cmd(daemon, &cmd); 1413 } 1414 1415 static int __cmd_signal(struct daemon *daemon, struct option parent_options[], 1416 int argc, const char **argv) 1417 { 1418 const char *name = "all"; 1419 struct option start_options[] = { 1420 OPT_STRING(0, "session", &name, "session", 1421 "Sent signal to specific session"), 1422 OPT_PARENT(parent_options), 1423 OPT_END() 1424 }; 1425 union cmd cmd; 1426 1427 argc = parse_options(argc, argv, start_options, daemon_usage, 0); 1428 if (argc) 1429 usage_with_options(daemon_usage, start_options); 1430 1431 if (setup_config(daemon)) { 1432 pr_err("failed: config not found\n"); 1433 return -1; 1434 } 1435 1436 memset(&cmd, 0, sizeof(cmd)); 1437 cmd.signal.cmd = CMD_SIGNAL, 1438 cmd.signal.sig = SIGUSR2; 1439 strncpy(cmd.signal.name, name, sizeof(cmd.signal.name) - 1); 1440 1441 return send_cmd(daemon, &cmd); 1442 } 1443 1444 static int __cmd_stop(struct daemon *daemon, struct option parent_options[], 1445 int argc, const char **argv) 1446 { 1447 struct option start_options[] = { 1448 OPT_PARENT(parent_options), 1449 OPT_END() 1450 }; 1451 union cmd cmd; 1452 1453 argc = parse_options(argc, argv, start_options, daemon_usage, 0); 1454 if (argc) 1455 usage_with_options(daemon_usage, start_options); 1456 1457 if (setup_config(daemon)) { 1458 pr_err("failed: config not found\n"); 1459 return -1; 1460 } 1461 1462 memset(&cmd, 0, sizeof(cmd)); 1463 cmd.cmd = CMD_STOP; 1464 return send_cmd(daemon, &cmd); 1465 } 1466 1467 static int __cmd_ping(struct daemon *daemon, struct option parent_options[], 1468 int argc, const char **argv) 1469 { 1470 const char *name = "all"; 1471 struct option ping_options[] = { 1472 OPT_STRING(0, "session", &name, "session", 1473 "Ping to specific session"), 1474 OPT_PARENT(parent_options), 1475 OPT_END() 1476 }; 1477 union cmd cmd; 1478 1479 argc = parse_options(argc, argv, ping_options, daemon_usage, 0); 1480 if (argc) 1481 usage_with_options(daemon_usage, ping_options); 1482 1483 if (setup_config(daemon)) { 1484 pr_err("failed: config not found\n"); 1485 return -1; 1486 } 1487 1488 memset(&cmd, 0, sizeof(cmd)); 1489 cmd.cmd = CMD_PING; 1490 scnprintf(cmd.ping.name, sizeof(cmd.ping.name), "%s", name); 1491 return send_cmd(daemon, &cmd); 1492 } 1493 1494 static char *alloc_perf_exe_path(void) 1495 { 1496 char path[PATH_MAX]; 1497 1498 perf_exe(path, sizeof(path)); 1499 return strdup(path); 1500 } 1501 1502 int cmd_daemon(int argc, const char **argv) 1503 { 1504 struct option daemon_options[] = { 1505 OPT_INCR('v', "verbose", &verbose, "be more verbose"), 1506 OPT_STRING(0, "config", &__daemon.config, 1507 "config file", "config file path"), 1508 OPT_STRING(0, "base", &__daemon.base_user, 1509 "directory", "base directory"), 1510 OPT_STRING_OPTARG('x', "field-separator", &__daemon.csv_sep, 1511 "field separator", "print counts with custom separator", ","), 1512 OPT_END() 1513 }; 1514 int ret = -1; 1515 1516 __daemon.perf = alloc_perf_exe_path(); 1517 if (!__daemon.perf) 1518 return -ENOMEM; 1519 1520 __daemon.out = stdout; 1521 1522 argc = parse_options(argc, argv, daemon_options, daemon_usage, 1523 PARSE_OPT_STOP_AT_NON_OPTION); 1524 1525 if (argc) { 1526 if (!strcmp(argv[0], "start")) 1527 ret = __cmd_start(&__daemon, daemon_options, argc, argv); 1528 else if (!strcmp(argv[0], "signal")) 1529 ret = __cmd_signal(&__daemon, daemon_options, argc, argv); 1530 else if (!strcmp(argv[0], "stop")) 1531 ret = __cmd_stop(&__daemon, daemon_options, argc, argv); 1532 else if (!strcmp(argv[0], "ping")) 1533 ret = __cmd_ping(&__daemon, daemon_options, argc, argv); 1534 else 1535 pr_err("failed: unknown command '%s'\n", argv[0]); 1536 } else { 1537 ret = setup_config(&__daemon); 1538 if (ret) 1539 pr_err("failed: config not found\n"); 1540 else 1541 ret = send_cmd_list(&__daemon); 1542 } 1543 zfree(&__daemon.perf); 1544 return ret; 1545 } 1546
Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.