Limit process cpu usage using cgroup

Reference

Limit process cpu usage using cgroup

limit_cpu_usage()
{
	local pid=$1
	if mount -l | grep -q cgroup2;then
		local cgroup_dir=$(mount -l | grep cgroup2 | awk '{print $3}' | head -n1)
		
		# Configure the system to mount cgroups-v2 by default during system boot by the systemd system and service manager:
		# grubby --update-kernel=/boot/vmlinuz-$(uname -r) --args="systemd.unified_cgroup_hierarchy=1"
		# grubby --update-kernel=ALL --args="systemd.unified_cgroup_hierarchy=1"
		
		# Enable CPU-related controllers for children groups:
		echo "+cpu" >> $cgroup_dir/cgroup.subtree_control
		echo "+cpuset" >> $cgroup_dir/cgroup.subtree_control
		
		# Create sub group
		mkdir $cgroup_dir/sub_g1
		# Enable the CPU-related controllers in /sys/fs/cgroup/sub_g1/ to obtain controllers that are relevant only to CPU:
		echo "+cpu" >> $cgroup_dir/sub_g1/cgroup.subtree_control
		echo "+cpuset" >> $cgroup_dir/sub_g1/cgroup.subtree_control
		
		# Create sub group
		mkdir $cgroup_dir/sub_g1/tasks
		
		# set usable cpus
		echo "1" > $cgroup_dir/sub_g1/tasks/cpuset.cpus
		
		# Configure CPU bandwidth to achieve resource restrictions within the control group:
		# The first value is the allowed time quota in microseconds for which all processes collectively in a child group can run during one period. 
		# The second value specifies the length of the period.
		# This command sets CPU time distribution controls so that all processes collectively in the /sys/fs/cgroup/sub_g1/tasks child group can run on the CPU for only 10% 
		# That is, one fifth of each second.
		echo "1000 10000" > $cgroup_dir/sub_g1/tasks/cpu.max
		
		# Add the applications' PIDs to the child group:
		echo "$pid" > $cgroup_dir/sub_g1/tasks/cgroup.procs
	elif mount -l | grep -q cgroup;then
		local cgroup_dir=$(mount -l | grep "tmpfs on.*cgroup" | awk '{print $3}')
		mkdir $cgroup_dir/cpu/sub_g1
		echo "10000" > $cgroup_dir/cpu/sub_g1/cpu.cfs_period_us
		echo "1000" > $cgroup_dir/cpu/sub_g1/cpu.cfs_quota_us

		# Add the applications' PIDs to the child group:
		echo "$pid" > $cgroup_dir/cpu/sub_g1/cgroup.procs

	else
		echo "cgroup not found"
		return 1
	fi
	# Verify that the applications run in the specified control group:
	cat /proc/$pid/cgroup
	
}

remove cgroup

undo_limit_cpu_usage()
{
	local pid=$1
	if mount -l | grep -q cgroup2;then
		local cgroup_dir=$(mount -l | grep cgroup2 | awk '{print $3}' | head -n1)
		# detach process
		echo $pid > $cgroup_dir/cgroup.procs
		#kill -9 $pid
		# rm cgroup dir
		rmdir $cgroup_dir/sub_g1/tasks
		rmdir $cgroup_dir/sub_g1
	elif mount -l | grep -q cgroup;then
                local cgroup_dir=$(mount -l | grep "tmpfs on.*cgroup" | awk '{print $3}')
		# process must terminate or can't delete cgroup
		kill -9 $pid
		# rm cgroup dir
                rmdir $cgroup_dir/cpu/sub_g1
	else
		echo "cgroup not found"
	fi
}