Changeset View
Changeset View
Standalone View
Standalone View
src/kcrash.cpp
Show First 20 Lines • Show All 41 Lines • ▼ Show 20 Line(s) | |||||
42 | #ifdef Q_OS_LINUX | 42 | #ifdef Q_OS_LINUX | ||
43 | #include <sys/poll.h> | 43 | #include <sys/poll.h> | ||
44 | #include <sys/prctl.h> | 44 | #include <sys/prctl.h> | ||
45 | #endif | 45 | #endif | ||
46 | 46 | | |||
47 | #include <kaboutdata.h> | 47 | #include <kaboutdata.h> | ||
48 | #include <kstartupinfo.h> | 48 | #include <kstartupinfo.h> | ||
49 | 49 | | |||
50 | #include <array> | ||||
51 | #include <algorithm> | ||||
52 | | ||||
50 | #include <QDebug> | 53 | #include <QDebug> | ||
51 | #include <QGuiApplication> | 54 | #include <QGuiApplication> | ||
52 | #include <QStandardPaths> | 55 | #include <QStandardPaths> | ||
53 | #include <QThread> | 56 | #include <QThread> | ||
54 | #include <QLibraryInfo> | 57 | #include <QLibraryInfo> | ||
55 | #include <QFile> | 58 | #include <QFile> | ||
56 | 59 | | |||
57 | #include <QLoggingCategory> | 60 | #include <QLoggingCategory> | ||
▲ Show 20 Lines • Show All 620 Lines • ▼ Show 20 Line(s) | 680 | if (!s_coreConfig->isProcess()) { | |||
678 | // Only exit if we don't forward to core dumps | 681 | // Only exit if we don't forward to core dumps | ||
679 | _exit(253); | 682 | _exit(253); | ||
680 | } | 683 | } | ||
681 | } | 684 | } | ||
682 | } | 685 | } | ||
683 | 686 | | |||
684 | static pid_t startDirectly(const char *argv[]) | 687 | static pid_t startDirectly(const char *argv[]) | ||
685 | { | 688 | { | ||
689 | char** environ_end; | ||||
bruns: move this to the lambda scope, you can also make the var name shorter then. | |||||
690 | for(environ_end = environ; *environ_end; ++environ_end) {} | ||||
691 | | ||||
apol: Use {} instead of ; for readability. | |||||
jpalecek: Done that. | |||||
692 | std::array<const char*, 1024> environ_data; //hope it's big enough | ||||
693 | if((unsigned)(environ_end - environ) +2 >= environ_data.size()) { | ||||
anthonyfieroni: Just use vector, get the size by `environ_end - environ` | |||||
No, that would be dynamic allocation, which is not safe in signal handlers. The whole purpose was to avoid it. jpalecek: No, that would be dynamic allocation, which is not safe in signal handlers. The whole purpose… | |||||
694 | fprintf(stderr, "environ_data in KCrash not big enough!\n"); | ||||
695 | return 0; | ||||
696 | } | ||||
697 | auto end = std::copy_if(environ, environ_end, environ_data.begin(), | ||||
698 | [](const char* s) { | ||||
bruns: `std::copy_if`, instead of a separate `remove_if` pass. | |||||
Thanks for that suggestion, updated accordingly. I admit I'm still more accustomed to the old ways of remove_if. jpalecek: Thanks for that suggestion, updated accordingly. I admit I'm still more accustomed to the old… | |||||
699 | static const char envvar[] = "KCRASH_AUTO_RESTARTED="; | ||||
700 | return strncmp(envvar, s, sizeof(envvar)-1) != 0; | ||||
701 | }); | ||||
702 | *end++ = "KCRASH_AUTO_RESTARTED=1"; | ||||
703 | *end++ = nullptr; | ||||
the part after the && can be removed when you include the '=' in the static string bruns: the part after the `&&` can be removed when you include the '=' in the static string | |||||
686 | pid_t pid = fork(); | 704 | pid_t pid = fork(); | ||
687 | switch (pid) { | 705 | switch (pid) { | ||
688 | case -1: | 706 | case -1: | ||
689 | fprintf(stderr, "KCrash failed to fork(), errno = %d\n", errno); | 707 | fprintf(stderr, "KCrash failed to fork(), errno = %d\n", errno); | ||
690 | return 0; | 708 | return 0; | ||
691 | case 0: | 709 | case 0: | ||
692 | setgroups(0, nullptr); // Remove any extraneous groups | 710 | setgroups(0, nullptr); // Remove any extraneous groups | ||
693 | if (setgid(getgid()) < 0 || setuid(getuid()) < 0) { | 711 | if (setgid(getgid()) < 0 || setuid(getuid()) < 0) { | ||
694 | _exit(253); // This cannot happen. Theoretically. | 712 | _exit(253); // This cannot happen. Theoretically. | ||
695 | } | 713 | } | ||
696 | #ifndef Q_OS_OSX | 714 | #ifndef Q_OS_OSX | ||
697 | closeAllFDs(); // We are in the child now. Close FDs unconditionally. | 715 | closeAllFDs(); // We are in the child now. Close FDs unconditionally. | ||
698 | #endif | 716 | #endif | ||
699 | setenv("KCRASH_AUTO_RESTARTED", "1", 1); | 717 | execvpe(argv[0], const_cast< char ** >(argv), const_cast<char**> (environ_data.data())); | ||
700 | execvp(argv[0], const_cast< char ** >(argv)); | | |||
701 | fprintf(stderr, "KCrash failed to exec(), errno = %d\n", errno); | 718 | fprintf(stderr, "KCrash failed to exec(), errno = %d\n", errno); | ||
702 | _exit(253); | 719 | _exit(253); | ||
703 | default: | 720 | default: | ||
704 | return pid; | 721 | return pid; | ||
705 | } | 722 | } | ||
706 | } | 723 | } | ||
707 | 724 | | |||
708 | /* | 725 | /* | ||
▲ Show 20 Lines • Show All 136 Lines • Show Last 20 Lines |
move this to the lambda scope, you can also make the var name shorter then.