Compare commits

...

11 Commits

Author SHA1 Message Date
01b247d7fa Nix Fix 2025-04-10 10:42:17 +03:00
Narvin Singh
e776588a92 Fix: Typo 2021-10-26 09:24:07 -04:00
Narvin Singh
fe52291eda Feat: Example to update all daemons 2021-10-26 09:18:04 -04:00
Narvin Singh
8d02ac14c9 Merge: feat-request-all 2021-10-25 22:53:41 -04:00
Narvin Singh
d19eaeb6e9 Refactor: DRY 2021-10-25 22:43:46 -04:00
Narvin Singh
1bf05d0972 Feat: Return a PID in edge cases
- Return the first ancestor PID if root_name is not found.
- Return the process' own PID if its own name is root_name.
2021-10-25 22:29:52 -04:00
Narvin Singh
b19495a93c Fix: Treat date +%S as decimal instead of octal
The number of seconds elapsed in the current minute given by date
is a 2-digit number. That means seconds 0 to 9 have a leading 0,
which causes them to be interpreted as octal numbers. This is not
intended, but doesn't actually break things (because 00 to 07 octal
are equivalent to 0 to 7 decimal) until second 8 or 9, at which point
we get an error because 08 and 09 are invalid octal numbers.
2021-02-16 14:10:37 -05:00
Narvin Singh
24554f2b69 Feat: Utility module
- Move function to show usage upon request and exit into module
- Move/create time functions
- Move function that maps module file names to module functions
- Move rpid into the module and rename it to root_pid
2021-01-23 23:20:56 -05:00
Narvin Singh
6c8cf878f7 Chore: Fix formatting 2021-01-18 14:15:21 -05:00
Narvin Singh
fdeb1696d0 Refactor: Use rpid will all default parameters 2021-01-04 14:55:45 -05:00
Narvin Singh
2ee11a5eac Feat: Send request to all daemons
Write the requests to all named pipes if the mod list begins with
'>>* '. This feature will probably not be merged into the main branch
because we have to search for the fifo files before each send, and if
the daemon for this login session exits, the scheduler will continue
running, which may not be desirable.
2021-01-03 01:10:16 -05:00
11 changed files with 182 additions and 46 deletions

View File

@ -67,8 +67,8 @@ Then schedule the CPU and memory usage to be updated every 5 seconds.
avds 'cpu mem' 5000 true &
```
Finally, you can add these commmands to your volume and brightness keybindings
to update the status when those keys are pressed. Note that these jobs don't
You can add these commmands to your volume and brightness keybindings to
update the status when those keys are pressed. Note that these jobs don't
need to be backgrounded since they run immediately and exit.
```Shell
@ -76,6 +76,15 @@ avds vol-amixer
avds bl
```
In case you have multiple daemons running, e.g., in different login sessions,
you can update them all simultaneously. This would have all running daemons
update the volume and backlight sections of their statuses at once.
```Shell
avds '>>* vol-amixer'
avds '>>* bl'
```
You can also bind keys to commands like those in the `cmd` directory to
perform actions and also update the status bar. For instance, you can bind
keys to these commands to control the backlight and volume while also updating

14
avdd
View File

@ -1,4 +1,4 @@
#!/bin/bash
#!/usr/bin/env bash
USAGE="
USAGE: avdd [<mod_list>='cpu mem bl vol-amixer bat dt'|-h|-[-]help]
@ -38,13 +38,15 @@ EXAMPLES:
avdd 'vol-amixer dt' '[<' '<' '>' '>]' &
"
DEFAULT_MOD_LIST='cpu mem bl vol-amixer bat dt'
DEFAULT_MOD_LIST='cpu mem vol-amixer bat dt'
DEFAULT_PRE=' '
DEFAULT_SEP_L='| '
DEFAULT_SEP_R=' '
DEFAULT_SUF=' '
MOD_DIR="$(dirname "$0")"/mod
FIFO=/tmp/avdd-fifo-"$("$(dirname "$0")"/rpid $$)"
DIR="$(dirname "$0")"
MOD_DIR="${DIR}/mod"
DAEMON="$(basename "$0")"
FIFO="/tmp/${DAEMON}-fifo-$("${DIR}/rpid" $$)"
mod_list="${1-${DEFAULT_MOD_LIST}}"
@ -78,7 +80,7 @@ for mod in "${mods[@]}"; do
fi
done
# Construct and display the status by looping over the cached values in order
# Construct and display the status by looping over the cached values in order
draw_status() {
local mod stat
for mod in "${stat_cache_ordered_mods[@]}"; do
@ -100,7 +102,7 @@ draw_status
# function to get the new value for that section of the status bar. If any
# of the new values are different from the cached ones, update the cache
# and redraw the status bar once after all the mods are processed.
process_mods () {
process_mods() {
local mod new_val is_changed
for mod in "$@"; do
if [[ -v stat_cache[${mod}] ]]; then

46
avds
View File

@ -1,11 +1,12 @@
#!/bin/bash
#!/usr/bin/env bash
USAGE="
USAGE: avds <mod_list|-h|-[-]help> [<when>] [<repeat>]
mod_list
A comma or space separated list of modules to request that
the daemon execute.
the daemon execute. If mod_list begins this '>>* ', then
requests are sent to all running daemons.
when The integer number of milliseconds to wait before sending the
request, or one of the following values:
@ -31,6 +32,10 @@ EXAMPLES:
avds 'vol,bl'
Send the previous requests to all running daemons.
avds '>>* vol,bl'
If there are cpu and memory usage modules named 'cpu' and 'mem'
that update the cpu and memory usage statuses, send a requst to
update both of those statuses every 5 seconds.
@ -44,10 +49,9 @@ EXAMPLES:
avds 'bat,dt' m true
"
DAEMON=avdd
FIFO=/tmp/"${DAEMON}"-fifo-"$("$(dirname "$0")"/rpid $$)"
# Convert integer milliseconds to floating point seconds
ms_to_s () {
ms_to_s() {
printf '%.3f' "${1}e-3"
}
@ -65,6 +69,15 @@ if [[ "${mod_list}" =~ ^(-h|-(-)?help)$ ]]; then
exit 0
fi
# Check if we will be sending requests to all daemons, or set the named pipe
# for this login session
if [[ "${mod_list}" =~ ^\>\>\*\ ]]; then
mod_list="${mod_list:4}"
is_request_all=1
else
fifo="/tmp/${DAEMON}-fifo-$("$(dirname "$0")/rpid" $$)"
fi
when="${2:-0}"
# Validate when
@ -87,7 +100,7 @@ while [[ "${first_run}" -eq 1 || -n "${repeat}" ]]; do
else
case "${when}" in
m)
sleep $((60 - $(date +%S)))
sleep $((60 - 10#$(date +%S)))
;;
h)
readarray -t ms < <(date +'%M%n%S')
@ -103,11 +116,24 @@ while [[ "${first_run}" -eq 1 || -n "${repeat}" ]]; do
fi
fi
# Write each command to the pipe
if [[ ! -p "${FIFO}" ]]; then
printf 'The daemon %s is not running\n' "${DAEMON}" 1>&2
exit 1
# Write each command to the named pipe for this login session
if [[ ! -v is_request_all ]]; then
if [[ ! -p "${fifo}" ]]; then
printf 'The daemon %s is not running\n' "${DAEMON}" 1>&2
exit 1
fi
printf '%s\n' "${mod_list}" >> "${fifo}"
# Write each command to all the daemon named pipes
else
readarray -d '' fifos \
< <(find /tmp -maxdepth 1 -type p -name "${DAEMON}-fifo-*" -print0)
if [[ "${#fifos[@]}" -eq 0 ]]; then
printf 'There are no daemons running\n' 1>&2
exit 1
fi
for fifo in "${fifos[@]}"; do
printf '%s\n' "${mod_list}" >> "${fifo}"
done
fi
printf '%s\n' "${mod_list}" >> "${FIFO}"
done

View File

@ -1,11 +1,11 @@
#!/bin/bash
#!/usr/bin/env bash
mod_bat () {
# Customizable configuration constants
local -r DEFAULT_CNT=1
local -r DEFAULT_PRE_PLG=' '
local -r DEFAULT_PRE_UPLG=' '
local -r DEFAULT_PRE_UNK=' '
local -r DEFAULT_PRE_PLG=$'\u26A1 '
local -r DEFAULT_PRE_UPLG=$'\u2755 '
local -r DEFAULT_PRE_UNK='?? '
local -r DEFAULT_SUF='%'
local -r cnt="${1:-${DEFAULT_CNT}}"

2
mod/bl
View File

@ -1,4 +1,4 @@
#!/bin/bash
#!/usr/bin/env bash
mod_bl () {
# Customizable configuration constants

View File

@ -1,8 +1,8 @@
#!/bin/bash
#!/usr/bin/env bash
mod_cpu () {
# Customizable configuration constants
local -r DEFAULT_PRE=' '
local -r DEFAULT_PRE=$'\U0001F7E9 '
local -r DEFAULT_SUF=''
local -r pre="${1-${DEFAULT_PRE}}"

2
mod/dt
View File

@ -1,4 +1,4 @@
#!/bin/bash
#!/usr/bin/env bash
mod_dt () {
# Customizable configuration constants

View File

@ -1,8 +1,8 @@
#!/bin/bash
#!/usr/bin/env bash
mod_mem () {
# Customizable configuration constants
local -r DEFAULT_PRE=' '
local -r DEFAULT_PRE=$'\U0001F9E0 '
local -r DEFAULT_SUF='%'
local -r pre="${1-${DEFAULT_PRE}}"

View File

@ -1,12 +1,12 @@
#!/bin/bash
#!/usr/bin/env bash
# Requires amixer from the alsa-utils package
mod_vol_amixer () {
# Customizable configuration constants
local -r DEFAULT_PRE_LOW=' '
local -r DEFAULT_PRE_HI=' '
local -r DEFAULT_PRE_MUTE=' '
local -r DEFAULT_PRE_LOW=$'\U0001F508 '
local -r DEFAULT_PRE_HI=$'\U0001F50A '
local -r DEFAULT_PRE_MUTE=$'\U0001F507 '
local -r DEFAULT_SUF='%'
local -r pre_low="${1-${DEFAULT_PRE_LOW}}"

32
rpid
View File

@ -1,4 +1,4 @@
#!/bin/bash
#!/usr/bin/env bash
USAGE='
USAGE: rpid <pid|-h|-[-]help> [<root_name>=login]
@ -22,6 +22,16 @@ EXAMPLES:
process.
rpid
Get the PID of the first ancestor of the current process, if there
is no ancestor named "not_a_process."
rpid $$ not_a_process
Get the PID of the current process itself, if it is named
"current_process."
rpid $$ current_process
'
# Validate the arguments
@ -40,25 +50,19 @@ fi
root_name="${2:-login}"
get_info() {
local -ri current_pid="$1"
if [[ ! -r "/proc/${current_pid}/status" ]]; then exit 1; fi
prev_pid="${pid}"
current_pid="${pid}"
while [[ "${name}" != "${root_name}" && -r "/proc/${current_pid}/status" ]]; do
mapfile info < \
<(grep --null -E -m 2 '^(Name|PPid):' "/proc/${current_pid}/status" \
| sort | cut -f 2)
name="${info[0]##[[:space:]]}"
name="${name%%[[:space:]]}"
ppid="${info[1]##[[:space:]]}"
ppid="${ppid%%[[:space:]]}"
}
next_pid="${pid}"
while [[ "${name}" != "${root_name}" && "${ppid}" -ne 1 ]]; do
get_info "${next_pid}";
name_pid="${next_pid}"
next_pid="${ppid}"
prev_pid="${current_pid}"
current_pid="${info[1]##[[:space:]]}"
current_pid="${current_pid%%[[:space:]]}"
done
printf '%s\n' "${prev_pid}"
if [[ "${name}" != "${root_name}" ]]; then exit 1; fi
printf '%s\n' "${name_pid}"

95
util Normal file
View File

@ -0,0 +1,95 @@
#!/usr/bin/env bash
if [[ -v IS_SOURCED_UTIL ]]; then return 0; fi
IS_SOURCED_UTIL=1
# Show the usage if requested and exit
maybe_show_usage_and_exit() {
local -r arg="${1}"
if [[ "${arg}" =~ ^(-h|-(-)?help)$ ]]; then
printf %s "${USAGE:-No help}" 1>&2
exit 0
fi
}
# Get the ms since the epoch until now
tick_now() {
local -r out_name="${1}"
printf -v "${out_name}" %.0f "$(date +%s.%N)"e3
}
# Get the ms since the epoch until the given at spec
tick_at() {
local -r out_name="${1}" at_spec="${2}"
local -i now_ms now_s h m s s_to_d
tick_now now_ms
if [[ "${at_spec}" =~ ^[0-9]+$ ]]; then
printf -v "${out_name}" %d $((now_ms + at_spec))
else
now_s=$((now_ms / 1000))
case "${at_spec}" in
m)
printf -v "${out_name}" %d $(((now_s + 60 - now_s % 60) * 1000))
;;
h)
printf -v "${out_name}" %d $(((now_s + 3600 - now_s % 3600) * 1000))
;;
d)
# Work off the local time to account for the timezone since the
# epoch is aligned to a UTC day boundary
read -r h m s < <(date +'%H %M %S')
s_to_d=$(((24 - h) * 3600 - m * 60 - s))
printf -v "${out_name}" %d $(((now_s + s_to_d) * 1000))
;;
*)
return 1
;;
esac
fi
}
# Get the ms from now until the given ms since the epoch
ms_until() {
local -r out_name="${1}" until_ms="${2}"
local -i now_ms
tick_now now_ms
printf -v "${out_name}" %d $((until_ms - now_ms))
}
# Convert integer milliseconds to floating point seconds
ms_to_s() {
local -r out_name="${1}"
local -ri ms="${2}"
printf -v "${out_name}" %.3f "${ms}e-3"
}
# Map the module file name to the module function
mod_to_fn() {
local -r out_name="${1}" file_name="${2}"
printf mod_%s "${file_name//-/_}"
}
# Get the pid of the ancestor process with the given name
root_pid() {
local -r out_name="${1}"
local -ri pid="${2:-$$}"
local -r root_name="${3:-login}"
local -i current_pid="${pid}"
local name
while [[ "${current_pid}" -ne 1 ]]; do
if [[ ! -r "/proc/${current_pid}/status" ]]; then return 1; fi
mapfile info < \
<('grep' --null -E -m 2 '^(Name|PPid):' "/proc/${current_pid}/status" \
| 'sort' | 'cut' -f 2)
name="${info[0]##[[:space:]]}"
name="${name%%[[:space:]]}"
if [[ "${name}" = "${root_name}" ]]; then
printf -v "${out_name}" %s "${current_pid}"
return 0
fi
current_pid="${info[1]##[[:space:]]}"
current_pid="${current_pid%%[[:space:]]}"
done
return 1
}