1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
|
/* Copyright (C) 2022 The Qt Company Ltd.
*
* SPDX-License-Identifier: GPL-3.0-only WITH Qt-GPL-exception-1.0
*/
#include <sys/stat.h>
#include <iostream>
#include <unistd.h>
#include <csignal>
#include <cstring>
#include "licenseservice.h"
#include "version.h"
using namespace QLicenseService;
std::unique_ptr<LicenseService> service;
void signalHandler(int signal)
{
if (!service)
exit(signal);
switch (signal) {
case SIGINT:
service->cancel();
break;
case SIGTERM:
service->cancel();
break;
default:
exit(signal);
}
}
int startProcess(uint16_t tcpPort) {
// Fire it up
service.reset(new LicenseService(tcpPort));
if (!(service->start() && service->waitForStarted())) {
std::cout << "Error while starting licenser: " << service->errorString() << std::endl;
return EXIT_FAILURE;
}
std::cout << "Started\n";
std::cout << "listening..\n";
if (!service->waitForFinished()) {
std::cout << "Error while stopping licenser: " << service->errorString() << std::endl;
return EXIT_FAILURE;
}
// Licenser runs infinitely if not interrupted
if (service->status() != LicenseService::Status::Canceled
&& service->status() != LicenseService::Status::Finished) {
std::cout << "Unexpected status for stopped licenser: " << service->errorString() << std::endl;
return EXIT_FAILURE;
}
return EXIT_SUCCESS;
}
int main(int argc, char *argv[])
{
signal(SIGINT, signalHandler);
signal(SIGTERM, signalHandler);
uint16_t tcpPort = 0;
// Get arguments
std::string message = "";
bool all_ok = true;
for (int i = 1; i < argc; i++) {
// If command-line parameter is "--nodaemon", start right away
// as normal CLI process (not as daemon)
if (strcmp(argv[1], "--nodaemon") == 0)
return startProcess(0);
// If command-line parameter is "--version", show the version and exit.
else if (strcmp(argv[1], "--version") == 0) {
std::cout << "Qt License Daemon (qtlicd) v" << DAEMON_VERSION << " "
<< COPYRIGHT_TEXT << std::endl;
return EXIT_SUCCESS;
}
else if (strcmp(argv[i], "--port") == 0) {
if (i + 1 == argc) {
all_ok = false;
printf("No port number given\n");
break;
}
try {
tcpPort = std::stoi(argv[i+1]);
i++;
}
catch (...) {
all_ok = false;
printf("Invalid port - must be an integer\n");
break;
}
}
else if (strcmp(argv[i], "--help") == 0) {
all_ok = false;
break;
}
else {
printf("Invalid argument: %s\n", argv[i]);
all_ok = false;
break;
}
}
if (!all_ok) {
printf("\nUsage: qtlicd [option] [value]\n");
printf("Supported options are:\n");
printf(" --port <port number> : Specify TCP/IP server port. If omitted, default is used.\n");
printf(" --nodaemon : Run in non-daemon mode (in console like any other CLI app)\n");
printf(" --version : Version info\n");
printf(" --help : This help\n\n");
return EXIT_FAILURE;
}
printf("Starting daemon\n");
// Fork process
pid_t pid, sid;
pid = fork();
if (pid > 0) {
return EXIT_SUCCESS;
}
else if (pid < 0) {
printf("Daemon process fork failed!\n");
return EXIT_FAILURE;
}
umask(0);
sid = setsid();
// Check session ID for the child process
if (sid < 0)
{
printf("Invalid session id for a child process\n");
return EXIT_FAILURE;
}
return startProcess(tcpPort);
}
|