Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to make a function work in background in bash / replace text / CPU usage

I have been playing around with the bashrc and one of the thing I want to see at all time is my cpu usage in percentage. I decided to set this data in my PS1. The problem is that to have an accurate estimation of my CPU usage I need to do operations that require waiting for at least 0.5 seconds.

As a result of this, my new command line only displays at the end of the CPU calculation, 0.5 seconds later, which is really not acceptable. To deal with this I thought that I could maybe use a thread to do the CPU calculation and only display it at the end but I don't know how to do so.

One of the problem is that I display other information after CPU percentage so I don't know if it is even possible to delay the CPU display while still displaying the rest of the command line. I thought that maybe I could display a temporary string such as ??.?? and then replace it by the real value but I am not sure how to do so since if I type commands fast the position of the ??.?? can change (for example typing ls 5 times in a row very fast).

Maybe there is an even simpler solution to my problem such as calculating the CPU percentage in an other way ?

My CPU percentage calculating function:

function cpuf(){
    NonIdle=0;Idle=0;Total=0;TotalD=0;Idled=0
    NonIdle=$((`cat /proc/stat | awk '/^cpu / {print$2+$3+$4+$7+$8+$9}'` - $NonIdle))
    Idle=$((`cat /proc/stat | awk '/^cpu / {print$5+$6}'` - $Idle))
    sleep 0.5
    NonIdle=$((`cat /proc/stat | awk '/^cpu / {print$2+$3+$4+$7+$8+$9}'` - $NonIdle))
    Idle=$((`cat /proc/stat | awk '/^cpu / {print$5+$6}'` - $Idle))
    Total=$((Idle+NonIdle))
    CPU=$(((Total-Idle)/Total))
    echo `echo "scale=2;($Total*100-$Idle*100)/$Total" | bc -l`
}

How I call it in the bashrc:

alias cpu="cpuf"
PS1+="(\[${MAGENTA}\]CPU $(cpu)%"
like image 441
PiggyGenius Avatar asked Apr 17 '26 07:04

PiggyGenius


1 Answers

There is no need to reinvent the wheel here, linux already takes care of capturing system stats in /proc/loadavg. The first number is average load in the last minute across all cpus, so we just need to divide by the number of cpus, which we can determine by reading /proc/cpuinfo. Rolling this into .bashrc we get:

.bashrc

...
# My fancy prompt, adjust as you like...
FANCY_PROMPT="$GREEN\u$YELLOW@\h:$PURPLE\w$BLUE$ $RESET"

CPUS=$( grep -c bogomips /proc/cpuinfo )

_prompt_command() {
    LOAD_AVG_1_MIN=$( cut -d ' ' -f 1 /proc/loadavg )
    PERCENT=$( echo "scale=0; $LOAD_AVG_1_MIN * 100 / $CPUS" | bc -l )
    PS1="CPU $PERCENT% $FANCY_PROMPT"
    true
}

PROMPT_COMMAND="_prompt_command"

In Use:

enter image description here

SO linux /proc/loadavg

like image 129
xxfelixxx Avatar answered Apr 18 '26 23:04

xxfelixxx