Программа выполняется по-разному при запуске в качестве службы systemctl - PullRequest
0 голосов
/ 04 июня 2019

У меня есть PHP-скрипт, выполнение которого занимает много времени (> 1 с).Я хочу выполнять один скрипт в секунду, независимо от того, завершился ли предыдущий или нет.Для этого я создал C-программу с pthread, например:

void *start_instance(void *_args)
{
    int id = abs(pthread_self());
    arg_for_script* args = _args ;

    printf("[SERVICE] start php script on thread %d\n",id);

    char cmd[200] ;

    sprintf(cmd, "php -f %s %d", args->script_path, id );

    system(cmd);

    printf("[SERVICE] end of script on thread %d\n", id);
    /* Pour enlever le warning */
    pthread_exit(NULL);
}

int main(int argc, char* argv[])
{


    if(argc < 2)
    {
        fprintf(stderr, "[SERVICE] Path of php script must be filled\n");
        return EXIT_FAILURE;
    }

    arg_for_script args ;
    args.script_path = argv[1];

    pthread_attr_t tattr ;
    pthread_attr_init(&tattr);
    pthread_attr_getinheritsched(&tattr, PTHREAD_EXPLICIT_SCHED);
    pthread_attr_getschedpolicy(&tattr, SCHED_RR);

    while(1) {
        pthread_t thrd;


        if(pthread_create(&thrd, &tattr, start_instance, (void *)&args) == -1) {
            fprintf(stderr, "[SERVICE] Unable to create thread\n");
            return EXIT_FAILURE;
        }


        sleep(1);
    }

    pthread_attr_destroy(&tattr);
    return EXIT_SUCCESS ;
}

, если я запускаю эту программу из командной строки:

./this_program path_of_php_script_as_argv.php

Она выполняется как исключение, у меня есть вывод какthis:

[SERVICE] start php script on thread 209983744
209983744 | START : Retrieving all new notifications..
209983744 | No new notification
[SERVICE] end of script on thread 209983744
[SERVICE] start php script on thread 218376448
218376448 | START : Retrieving all new notifications..
218376448 | No new notification
[SERVICE] end of script on thread 218376448
[SERVICE] start php script on thread 226769152
226769152 | START : Retrieving all new notifications..
226769152 | No new notification
[SERVICE] end of script on thread 226769152
[SERVICE] start php script on thread 235161856
235161856 | START : Retrieving all new notifications..
235161856 | No new notification
[SERVICE] end of script on thread 235161856
[SERVICE] start php script on thread 243554560
243554560 | START : Retrieving all new notifications..
243554560 | No new notification
[SERVICE] end of script on thread 243554560

Теперь я преобразовал эту программу в службу systemctl, чтобы выполнять ее все время в фоновом режиме, но когда я journalctl --follow (чтобы увидеть вывод systemctl), вот что я получаю:

Jun 04 15:12:05 vps559055 start[6116]: [SERVICE] start php script on thread 532399872
Jun 04 15:12:05 vps559055 start[6116]: [SERVICE] end of script on thread 532399872
Jun 04 15:12:05 vps559055 start[6116]: [SERVICE] start php script on thread 521811712
Jun 04 15:12:05 vps559055 start[6116]: [SERVICE] end of script on thread 521811712
Jun 04 15:12:05 vps559055 start[6116]: [SERVICE] start php script on thread 513419008
Jun 04 15:12:05 vps559055 start[6116]: [SERVICE] end of script on thread 513419008
Jun 04 15:12:05 vps559055 start[6116]: [SERVICE] start php script on thread 505026304
Jun 04 15:12:05 vps559055 start[6116]: [SERVICE] end of script on thread 505026304
Jun 04 15:12:05 vps559055 start[6116]: [SERVICE] start php script on thread 496633600
// ..... ~100 times, in the same second ! 
// then, second per second : 
Jun 04 15:12:05 vps559055 start[6116]: [SE83728128 | START : Retrieving all new notifications..
Jun 04 15:12:05 vps559055 start[6116]: 83728128 | No new notification
Jun 04 15:12:06 vps559055 start[6116]: 75335424 | START : Retrieving all new notifications..
Jun 04 15:12:06 vps559055 start[6116]: 75335424 | No new notification
Jun 04 15:12:07 vps559055 start[6116]: 66942720 | START : Retrieving all new notifications..
Jun 04 15:12:07 vps559055 start[6116]: 66942720 | No new notification
Jun 04 15:12:08 vps559055 start[6116]: 58550016 | START : Retrieving all new notifications..
Jun 04 15:12:08 vps559055 start[6116]: 58550016 | No new notification
Jun 04 15:12:09 vps559055 start[6116]: 50157312 | START : Retrieving all new notifications..
Jun 04 15:12:09 vps559055 start[6116]: 50157312 | No new notification
Jun 04 15:12:10 vps559055 start[6116]: 41764608 | START : Retrieving all new notifications..
Jun 04 15:12:10 vps559055 start[6116]: 41764608 | No new notification

все потоки C выполняются в одно и то же время (одна и та же секунда в журналах), но сценарии php выполняются секунды в секунду.Знаете ли вы, почему исполнение этих программ отличается?

РЕДАКТИРОВАТЬ: Воспроизводимый пример: создайте скрипт php script.php, содержащий:

$thid = $argv[1]?:null;
echo "php : START PHP SCRIPT ON THREADID $thid\n";
for($i = 0; $i < 3000000; $i++); // work .. 
echo "php : END PHP SCRIPT ON THREADID $thid\n";

exit ;

Создайте файл main.c, содержащий приведенный выше код, и скомпилируйте его:

gcc main.c -o start -lpthread

Когда вы запускаете ./start, все выводится как исключение:

[SERVICE] start php script on thread 861141248
php : START PHP SCRIPT ON THREADID 861141248
php : END PHP SCRIPT ON THREADID 861141248
[SERVICE] end of script on thread 861141248
[SERVICE] start php script on thread 939526400
php : START PHP SCRIPT ON THREADID 939526400
php : END PHP SCRIPT ON THREADID 939526400
[SERVICE] end of script on thread 939526400

теперь создайте службу systemd, используя этот файл конфигурации:

Description=My Service
After=network-online.target

[Service]
Type=simple
ExecStart=/path/to/c/program /path/to/php/script
Restart=on-failure

# Configures the time to wait before service is stopped forcefully.
TimeoutStopSec=300

[Install]
WantedBy=multi-user.target

Вывод должен быть тем, что я получаю:

Jun 05 13:03:00 vps559055 start[4491]: php : START PHP SCRIPT ON THREADID 1259825408
Jun 05 13:03:00 vps559055 start[4491]: php : END PHP SCRIPT ON THREADID 1259825408
// about one second later 
Jun 05 13:03:01 vps559055 start[4491]: php : START PHP SCRIPT ON THREADID 1268218112
Jun 05 13:03:01 vps559055 start[4491]: php : END PHP SCRIPT ON THREADID 1268218112
// ...
// same about 50 times 
// ...
// then suddenly, i got : 
Jun 05 13:03:32 vps559055 start[4491]: [SERVICE] start php script on thread 1175898368
Jun 05 13:03:32 vps559055 start[4491]: [SERVICE] end of script on thread 1175898368
Jun 05 13:03:32 vps559055 start[4491]: [SERVICE] start php script on thread 1184291072
Jun 05 13:03:32 vps559055 start[4491]: [SERVICE] end of script on thread 1184291072
Jun 05 13:03:32 vps559055 start[4491]: [SERVICE] start php script on thread 1192683776
Jun 05 13:03:32 vps559055 start[4491]: [SERVICE] end of script on thread 1192683776
//...
// again about 50 times, IN THE SAME SECOND, all this output 
// ...

Почему выходные данные становятся настолько беспорядочными, когда программа выполняется как фоновая служба systemd?...

...