core: introduce support for cgroup freezer
With cgroup v2 the cgroup freezer is implemented as a cgroup attribute called cgroup.freeze. cgroup can be frozen by writing "1" to the file and kernel will send us a notification through "cgroup.events" after the operation is finished and processes in the cgroup entered quiescent state, i.e. they are not scheduled to run. Writing "0" to the attribute file does the inverse and process execution is resumed. This commit exposes above low-level functionality through systemd's DBus API. Each unit type must provide specialized implementation for these methods, otherwise, we return an error. So far only service, scope, and slice unit types provide the support. It is possible to check if a given unit has the support using CanFreeze() DBus property. Note that DBus API has a synchronous behavior and we dispatch the reply to freeze/thaw requests only after the kernel has notified us that requested operation was completed.
This commit is contained in:
@@ -114,6 +114,9 @@ typedef struct Unit {
|
||||
UnitLoadState load_state;
|
||||
Unit *merged_into;
|
||||
|
||||
FreezerState freezer_state;
|
||||
sd_bus_message *pending_freezer_message;
|
||||
|
||||
char *id; /* One name is special because we use it for identification. Points to an entry in the names set */
|
||||
char *instance;
|
||||
|
||||
@@ -483,6 +486,11 @@ typedef struct UnitVTable {
|
||||
/* Clear out the various runtime/state/cache/logs/configuration data */
|
||||
int (*clean)(Unit *u, ExecCleanMask m);
|
||||
|
||||
/* Freeze the unit */
|
||||
int (*freeze)(Unit *u);
|
||||
int (*thaw)(Unit *u);
|
||||
bool (*can_freeze)(Unit *u);
|
||||
|
||||
/* Return which kind of data can be cleaned */
|
||||
int (*can_clean)(Unit *u, ExecCleanMask *ret);
|
||||
|
||||
@@ -695,6 +703,8 @@ const char *unit_status_string(Unit *u) _pure_;
|
||||
bool unit_has_name(const Unit *u, const char *name);
|
||||
|
||||
UnitActiveState unit_active_state(Unit *u);
|
||||
FreezerState unit_freezer_state(Unit *u);
|
||||
int unit_freezer_state_kernel(Unit *u, FreezerState *ret);
|
||||
|
||||
const char* unit_sub_state_to_string(Unit *u);
|
||||
|
||||
@@ -878,6 +888,16 @@ void unit_destroy_runtime_directory(Unit *u, const ExecContext *context);
|
||||
int unit_clean(Unit *u, ExecCleanMask mask);
|
||||
int unit_can_clean(Unit *u, ExecCleanMask *ret_mask);
|
||||
|
||||
bool unit_can_freeze(Unit *u);
|
||||
int unit_freeze(Unit *u);
|
||||
void unit_frozen(Unit *u);
|
||||
|
||||
int unit_thaw(Unit *u);
|
||||
void unit_thawed(Unit *u);
|
||||
|
||||
int unit_freeze_vtable_common(Unit *u);
|
||||
int unit_thaw_vtable_common(Unit *u);
|
||||
|
||||
/* Macros which append UNIT= or USER_UNIT= to the message */
|
||||
|
||||
#define log_unit_full(unit, level, error, ...) \
|
||||
|
||||
Reference in New Issue
Block a user