Skip to content

Commit 2d76175

Browse files
committed
Added the ability to manage resources through plugins.
1 parent 2363658 commit 2d76175

2 files changed

Lines changed: 110 additions & 0 deletions

File tree

lib/services/services_linux.c

Lines changed: 107 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,10 +19,14 @@
1919
#include <errno.h>
2020
#include <unistd.h>
2121
#include <dirent.h>
22+
#include <dlfcn.h>
2223
#include <grp.h>
2324
#include <string.h>
2425
#include <sys/time.h>
2526
#include <sys/resource.h>
27+
#include <sys/mman.h>
28+
#include <fcntl.h>
29+
2630

2731
#include "crm/crm.h"
2832
#include "crm/common/mainloop.h"
@@ -1174,6 +1178,10 @@ services__execute_file(svc_action_t *op)
11741178
struct stat st;
11751179
struct sigchld_data_s data;
11761180

1181+
if (services__execute_file_as_plugin(op) == pcmk_rc_ok){
1182+
return pcmk_rc_ok;
1183+
}
1184+
11771185
// Catch common failure conditions early
11781186
if (stat(op->opaque->exec, &st) != 0) {
11791187
rc = errno;
@@ -1436,3 +1444,102 @@ services_os_get_directory_list(const char *root, gboolean files, gboolean execut
14361444

14371445
return result;
14381446
}
1447+
1448+
int
1449+
services__execute_file_as_plugin(svc_action_t *op) {
1450+
void *handle;
1451+
int (*exec)(int, int, char *);
1452+
char *lib_error;
1453+
int exec_status;
1454+
char dst[200] = "/usr/lib/ocf/resource.d/heartbeat/";
1455+
strcat(dst, op->agent);
1456+
handle = dlopen (dst, RTLD_NOW | RTLD_LOCAL);
1457+
1458+
if (!handle) {
1459+
// можно что-то залогировать
1460+
return pcmk_rc_error;
1461+
} else {
1462+
// можно что-то залогировать
1463+
exec = dlsym(handle, "handler");
1464+
1465+
if ((lib_error = dlerror()) != NULL){
1466+
free(lib_error);
1467+
1468+
// можно что-то залогировать
1469+
// ситуация, когда мы смогли открыть агента
1470+
// как разделяемую библиотеку, но не нашли
1471+
// нужного метода (что-то странное)
1472+
return pcmk_rc_error;
1473+
} else {
1474+
char num[10];
1475+
int out_fd;
1476+
int err_fd;
1477+
char out_file_name[100] = "outfd-";
1478+
char err_file_name[100] = "errfd-";
1479+
1480+
add_action_env_vars(op);
1481+
1482+
sprintf(num, "%d", getpid());
1483+
strcat(out_file_name, num);
1484+
strcat(err_file_name, num);
1485+
1486+
out_fd = memfd_create(out_file_name, MFD_ALLOW_SEALING);
1487+
err_fd = memfd_create(err_file_name, MFD_ALLOW_SEALING);
1488+
1489+
exec_status = exec(out_fd, err_fd, op->action);
1490+
{
1491+
int size_out = lseek(out_fd, 0, SEEK_END); // SEEK_CUR ?
1492+
int size_err = lseek(err_fd, 0, SEEK_END);
1493+
if (size_out > 0) {
1494+
char *buf_out = (char *)malloc(sizeof(char) * (size_out + 1));
1495+
lseek(out_fd, 0, SEEK_SET);
1496+
if (read(out_fd, buf_out, size_out) >= 0) {
1497+
buf_out[size_out] = '\0';
1498+
op->stdout_data = buf_out;
1499+
}
1500+
} else {
1501+
op->stdout_data = NULL;
1502+
}
1503+
1504+
if (size_err > 0) {
1505+
char *buf_err = (char *)malloc(sizeof(char) * (size_err + 1));
1506+
lseek(err_fd, 0, SEEK_SET);
1507+
if (read(err_fd, buf_err, size_err) >= 0) {
1508+
buf_err[size_err] = '\0';
1509+
op->stderr_data = buf_err;
1510+
}
1511+
} else {
1512+
op->stderr_data = NULL;
1513+
}
1514+
1515+
if (close(out_fd) < 0) {
1516+
crm_info("Error '%s'", "a");
1517+
}
1518+
if (close(err_fd) < 0) {
1519+
crm_info("Error 's'", "b");
1520+
}
1521+
1522+
op->rc = exec_status;
1523+
op->status = PCMK_EXEC_DONE;
1524+
op->pid = 0;
1525+
if (op->interval_ms != 0) {
1526+
// Recurring operations must be either cancelled or rescheduled
1527+
if (op->cancel) {
1528+
services__set_cancelled(op);
1529+
cancel_recurring_action(op);
1530+
} else {
1531+
op->opaque->repeat_timer = g_timeout_add(op->interval_ms,
1532+
recurring_action_timer,
1533+
(void *) op);
1534+
}
1535+
}
1536+
if (op->opaque->callback) {
1537+
op->opaque->callback(op);
1538+
}
1539+
}
1540+
dlclose(handle);
1541+
return pcmk_rc_ok;
1542+
//dlclose(handle);
1543+
}
1544+
}
1545+
}

lib/services/services_private.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,9 @@ GList *services_os_get_directory_list(const char *root, gboolean files, gboolean
5757
G_GNUC_INTERNAL
5858
int services__execute_file(svc_action_t *op);
5959

60+
G_GNUC_INTERNAL
61+
int services__execute_file_as_plugin(svc_action_t *op);
62+
6063
G_GNUC_INTERNAL
6164
gboolean cancel_recurring_action(svc_action_t * op);
6265

0 commit comments

Comments
 (0)