diff --git a/package/lean/cpufreq/Makefile b/package/lean/cpufreq/Makefile new file mode 100644 index 0000000000000..c71f1f36f2f04 --- /dev/null +++ b/package/lean/cpufreq/Makefile @@ -0,0 +1,30 @@ +# SPDX-License-Identifier: GPL-2.0-only +# +# Copyright (C) 2024 ImmortalWrt.org + +include $(TOPDIR)/rules.mk + +PKG_NAME:=cpufreq +PKG_RELEASE:=1 + +include $(INCLUDE_DIR)/package.mk + +define Package/cpufreq + TITLE:=CPU Frequency Scaling adjustment tool + DEPENDS:=@(arm||aarch64) + PKGARCH:=all +endef + +define Build/Compile +endef + +define Package/cpufreq/install + $(INSTALL_DIR) $(1)/etc/config + $(INSTALL_CONF) $(CURDIR)/files/cpufreq.config $(1)/etc/config/cpufreq + $(INSTALL_DIR) $(1)/etc/init.d + $(INSTALL_BIN) $(CURDIR)/files/cpufreq.init $(1)/etc/init.d/cpufreq + $(INSTALL_DIR) $(1)/etc/uci-defaults + $(INSTALL_BIN) $(CURDIR)/files/cpufreq.uci $(1)/etc/uci-defaults/10-cpufreq +endef + +$(eval $(call BuildPackage,cpufreq)) diff --git a/package/lean/cpufreq/files/cpufreq.config b/package/lean/cpufreq/files/cpufreq.config new file mode 100644 index 0000000000000..9004f1bd87633 --- /dev/null +++ b/package/lean/cpufreq/files/cpufreq.config @@ -0,0 +1,5 @@ + +config settings 'cpufreq' + +config settings 'global' + diff --git a/package/lean/cpufreq/files/cpufreq.init b/package/lean/cpufreq/files/cpufreq.init new file mode 100755 index 0000000000000..fc5dc47776abf --- /dev/null +++ b/package/lean/cpufreq/files/cpufreq.init @@ -0,0 +1,58 @@ +#!/bin/sh /etc/rc.common + +START=15 +USE_PROCD=1 + +NAME="cpufreq" +CPUFREQ_PATH="/sys/devices/system/cpu/cpufreq" + +extra_command "get_policies" "Get CPU scaling governors and frequencies" + +get_policies() { + json_init + for policy in $(ls -d "$CPUFREQ_PATH"/policy[0-9]* 2>"/dev/null"); do + [ -s "$policy/scaling_available_frequencies" ] || continue + json_add_object "$(basename "$policy")" + json_add_string "index" "$(basename "$policy" | grep -Eo "[0-9]*$")" + json_add_string "cpus" "$(cat "$policy/affected_cpus")" + json_add_array "freqs" + for freq in $(cat "$policy/scaling_available_frequencies"); do + json_add_string "" "$freq" + done + json_close_array + json_add_array "governors" + for governor in $(cat "$policy/scaling_available_governors"); do + json_add_string "" "$governor" + done + json_close_array + json_close_object + done + json_dump +} + +write_cpufreq_config() { + local value + config_get value "$NAME" "$1" + [ -z "$value" ] || echo -n "$value" > "$2" +} + +start_service() { + config_load "$NAME" + + for i in $(ls -d "$CPUFREQ_PATH"/policy[0-9]* 2>"/dev/null" | grep -Eo "[0-9]*$") + do + [ -z "$(config_get "$NAME" "governor$i")" ] && return + + write_cpufreq_config "governor$i" "$CPUFREQ_PATH/policy$i/scaling_governor" + write_cpufreq_config "minfreq$i" "$CPUFREQ_PATH/policy$i/scaling_min_freq" + write_cpufreq_config "maxfreq$i" "$CPUFREQ_PATH/policy$i/scaling_max_freq" + if [ "$(config_get "$NAME" "governor$i")" = "ondemand" ]; then + write_cpufreq_config "sdfactor$i" "$CPUFREQ_PATH/ondemand/sampling_down_factor" + write_cpufreq_config "upthreshold$i" "$CPUFREQ_PATH/ondemand/up_threshold" + fi + done +} + +service_triggers() { + procd_add_reload_trigger "$NAME" +} diff --git a/package/lean/cpufreq/files/cpufreq.uci b/package/lean/cpufreq/files/cpufreq.uci new file mode 100644 index 0000000000000..4ee49c9314e1b --- /dev/null +++ b/package/lean/cpufreq/files/cpufreq.uci @@ -0,0 +1,75 @@ +#!/bin/sh + +uci_write_config() { + uci -q set "cpufreq.cpufreq.governor$1"="$2" + uci -q set "cpufreq.cpufreq.minfreq$1"="$3" + uci -q set "cpufreq.cpufreq.maxfreq$1"="$4" + [ -n "$5" ] && uci -q set "cpufreq.cpufreq.sdfactor$1"="$5" + [ -n "$6" ] && uci -q set "cpufreq.cpufreq.upthreshold$1"="$6" + uci -q commit cpufreq +} + +[ "$(uci -q get cpufreq.global.set)" -eq "1" ] && exit 0 + +CPU_FREQS="$(cat '/sys/devices/system/cpu/cpufreq/policy0/scaling_available_frequencies')" +CPU_MIN_FREQ="$(cat '/sys/devices/system/cpu/cpufreq/policy0/scaling_min_freq')" +CPU_MAX_FREQ="$(cat '/sys/devices/system/cpu/cpufreq/policy0/scaling_max_freq')" +CPU_POLICYS="$(find '/sys/devices/system/cpu/cpufreq/policy'* -maxdepth 0 | grep -Eo '[0-9]+')" + +source "/etc/openwrt_release" +case "$DISTRIB_TARGET" in + "bcm27xx/bcm2710"|\ + "bcm27xx/bcm2711") + uci_write_config 0 ondemand 600000 "$CPU_MAX_FREQ" 10 50 + ;; + "ipq40xx/generic") + uci_write_config 0 performance 200000 "$CPU_MAX_FREQ" + ;; + "ipq806x/generic") + uci_write_config 0 performance 600000 "$CPU_MAX_FREQ" + # IPQ8064/5 + echo "$CPU_POLICYS" | grep -q "1" && uci_write_config 1 performance 600000 1200000 + ;; + "mediatek/mt7622") + uci_write_config 0 ondemand 600000 1350000 10 50 + ;; + "qualcommax/ipq60xx"|\ + "qualcommax/ipq807x") + uci_write_config 0 schedutil "$CPU_MIN_FREQ" "$CPU_MAX_FREQ" + ;; + "rockchip/armv8") + if echo "$CPU_POLICYS" | grep -q "6"; then + # RK3588/S + uci_write_config 0 schedutil 1008000 1800000 + uci_write_config 4 schedutil 816000 2208000 + uci_write_config 6 schedutil 816000 2208000 + elif echo "$CPU_POLICYS" | grep -q "4"; then + # RK3399 + uci_write_config 0 schedutil 600000 1608000 + uci_write_config 4 schedutil 600000 2016000 + else + if ! echo "$CPU_FREQS" | grep -q "1992000"; then + # RK3328 + CPU_MAX_FREQ="1512000" + fi + uci_write_config 0 schedutil 816000 "$CPU_MAX_FREQ" + fi + ;; + "sunxi/cortexa53") + if echo "$CPU_FREQS" | grep -q "1800000"; then + # H6 + uci_write_config 0 schedutil "888000" "$CPU_MAX_FREQ" + elif echo "$CPU_FREQS" | grep -q "1512000"; then + # H616/8 + uci_write_config 0 schedutil "936000" "1512000" + elif echo "$CPU_FREQS" | grep -q "1296000"; then + # H5 + uci_write_config 0 ondemand "$CPU_MIN_FREQ" "1296000" 10 50 + else + # A64 + uci_write_config 0 ondemand "$CPU_MIN_FREQ" "$CPU_MAX_FREQ" 10 50 + fi + ;; +esac + +exit 0