Compare commits

...

140 commits
v1.3.0 ... main

Author SHA1 Message Date
Jakob P. Liljenberg 3d46dc6969
Merge pull request #838 from imwints/freebsd-static
Add missing linker flag for static links on FreeBSD
2024-05-13 23:05:12 +02:00
Steffen Winter b93206f038
Add missing linker flag for static links on FreeBSD
https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=278551
2024-05-13 22:47:03 +02:00
Jakob P. Liljenberg ac62ba9de1
Merge pull request #840 from aristocratos/fix/zero_temp 2024-05-13 19:10:17 +02:00
Jakob P. Liljenberg 3f917c0412
Merge pull request #850 from acidghost/theme-comments 2024-05-13 19:08:45 +02:00
Andrea Jemmett 0127e8b3cd Fix comments in theme files 2024-05-12 16:09:09 +02:00
Jos Dehaes ebc86e9702 fix zero temp (#467) 2024-05-04 20:59:04 +02:00
aristocratos dd4ada7023 Fixed missing definition for ROCm static build 2024-05-01 20:43:46 +02:00
aristocratos b48bf6ae45 Add info text about regex filtering in help menu 2024-04-30 18:03:06 +02:00
Jakob P. Liljenberg 3b65b3a729
Merge pull request #806 from imwints/regex-search 2024-04-30 17:21:07 +02:00
Steffen 255b777563
Add regex filtering
Filters starting with '!' will try to match processes pid, name, cmd and
user with extended regex as defined by the C++ standard. A single '!'
will not filter.
2024-04-30 17:09:15 +02:00
Jakob P. Liljenberg 8c1a8ab4fa
Merge pull request #836 from vsey/Fix-Typo 2024-04-30 17:02:46 +02:00
Jakob P. Liljenberg f8cfa70dda
Merge branch 'main' into Fix-Typo 2024-04-30 17:02:16 +02:00
Jakob P. Liljenberg 3a6f816396
Merge pull request #835 from imwints/battery 2024-04-30 17:01:02 +02:00
vsey 14b388521d
Fix typo 2024-04-30 16:09:37 +02:00
Steffen Winter d200ce45ae
Show time in days when remaining battery exceeds an estimation of 24h 2024-04-30 15:32:41 +02:00
Jakob P. Liljenberg 924c3f3a72
Merge pull request #819 from kalkafox/rsmi-pwr-usage-fix
fix pwr_usage not being defined correctly during rsmi collection
2024-04-28 22:45:42 +02:00
Jakob P. Liljenberg 0e07debb7d
Merge pull request #831 from thecoder-001/main
macOS: fix crash if there exists a uid not associated with any user
2024-04-28 22:38:28 +02:00
Jakob P. Liljenberg b991e6898d
Merge pull request #832 from imwints/macos-ci
Fix brew not finding LLVM path after release of LLVM 18
2024-04-28 22:36:39 +02:00
Steffen Winter 5d7794019a
Fix brew not finding LLVM path after release of LLVM 18 2024-04-28 22:28:31 +02:00
thecoder-001 5ba45f7633
Remove logging for uid without username
Signed-off-by: thecoder-001 <ayush06feb@gmail.com>
2024-04-28 23:53:27 +05:30
thecoder-001 9a37395744
osx: show uid instead of 'unknown' if no user exists with the same
Signed-off-by: thecoder-001 <ayush06feb@gmail.com>
2024-04-28 02:53:50 +05:30
thecoder-001 08f90fb4f0
fix: crash on osx proc box
Signed-off-by: thecoder-001 <ayush06feb@gmail.com>
2024-04-28 02:41:20 +05:30
Kalka b06474136b fix pwr_usage not being defined correctly during rsmi collection 2024-04-11 22:50:58 -04:00
Jakob P. Liljenberg d1680735d9
Merge pull request #796 from davc0n/main 2024-03-23 01:42:17 +01:00
Jakob P. Liljenberg a535a6eb92
Merge pull request #797 from kz6fittycent/main 2024-03-23 01:37:59 +01:00
Jakob P. Liljenberg b1b8249d55
Merge pull request #807 from kk9uk/main 2024-03-23 01:35:52 +01:00
kk9uk 4a82105547 [FEATURE] Add gruvbox_light theme 2024-03-20 12:17:24 +08:00
kz6fittycent 8af8389bd0
Merge branch 'aristocratos:main' into main 2024-03-13 11:02:55 -05:00
kz6fittycent adaea59a2a
Update test-snap-can-build.yml 2024-03-13 10:50:29 -05:00
kz6fittycent 2aa2c90f41
Update snapcraft.yaml
core22 attempt
2024-03-13 10:49:38 -05:00
Davide Conti a60c969533 Fix rsmi device name buffer size
ref. issue #794
2024-03-13 10:12:28 +01:00
Jakob P. Liljenberg c767099d76
Merge pull request #724 from ottok/man-page 2024-03-04 18:03:27 +01:00
Otto Kekäläinen d8c054d92f Add 'lowdown' to build dependencies so GitHub actions actually runs it
Building the man page is optional and happens automatically if command
'lowdown' is present on the system. Add it to all possible GitHub CI files
so man page conversion will be tested and fully used.

Unfortunately 'lowdown' cannot be added to the musl jobs the program is
available only starting from Alpine v3.15, while the musl Docker images
run Alpine v3.14 (and haven't been updated in 2+ years).

Also, the Snap build used Ubuntu 20.04 "Focal" which equally is too old
to include Lowdown, which is available only from Ubuntu 22.04 "Jammy"
onward:
https://packages.ubuntu.com/search?suite=all&searchon=names&keywords=lowdown
2024-03-03 17:14:13 -08:00
Otto Kekäläinen ed68589af1 Create man page for btop in Markdown
Create a man page in Markdown format so that it can be read online on
GitHub etc and it can be edited much more easily than a raw troff/groff
file.

Compile it to proper man page format at build-time using 'lowdown' if
it is available on the system, otherwise just issue a warning in yellow.

Tested to work both with:

    export VERBOSE=1
    make
    make install
    make uninstall

    cmake -B build
    cmake --build build --verbose

While Lowdown is easy to manually install in all modern Linux distros
and also Homebrew for Mac, this commit does not add 'lowdown' in any
build dependencies or in the CI, that needs to be done separately.
2024-03-03 15:37:35 -08:00
Jakob P. Liljenberg c6fbfd1e27
Merge pull request #723 from ottok/fix-spelling 2024-03-01 07:58:12 +01:00
Otto Kekäläinen bfe8c20ebe Fix misc spelling 2024-02-29 22:11:39 -08:00
Jakob P. Liljenberg 6c66740290
Merge pull request #734 from imwints/build-info 2024-02-18 14:25:11 +01:00
Jakob P. Liljenberg 967ea1ab6f
Merge branch 'main' into build-info 2024-02-18 14:19:05 +01:00
Jakob P. Liljenberg cf609175fb
Merge pull request #763 from imwints/cmake-bump 2024-02-18 14:08:31 +01:00
Jakob P. Liljenberg e1575a1fca
Merge pull request #771 from Derppening/fix/linux-battery-wattage 2024-02-18 12:56:19 +01:00
David Mak e031cce6ba collect: Fix reading of battery power draw on Linux
This was erroneously set to read from the current battery charge.

Fixes #770.
2024-02-14 01:01:40 +08:00
Steffen Winter 83739f84e1
cmake: Remove version specifier 2024-02-12 23:56:43 +01:00
aristocratos fd2a2acdad v1.3.2 Hotfix GPU support AMD ROCm v6 2024-02-12 16:30:09 +01:00
Jakob P. Liljenberg 37d217eeb6
Merge pull request #762 from imwints/fix-rocm-github-link 2024-02-12 16:11:51 +01:00
Jakob P. Liljenberg f537715d8b
Merge branch 'main' into fix-rocm-github-link 2024-02-12 16:11:28 +01:00
Jakob P. Liljenberg 7a058e4f42
Merge pull request #761 from imwints/fix-rocm-5-6-supported 2024-02-12 16:09:50 +01:00
aristocratos bae006e94c Fixed variable names 2024-02-12 15:37:31 +01:00
aristocratos c625d512e1 Add check for possible librocm_smi64.so.6 and check for version 7 in the function logic 2024-02-12 15:31:43 +01:00
Steffen Winter 43af034317
fix: Can't detect librocm 6.0.x
librocm reports it's version as 7.0.0.0 in the 6.0.x release series.
2024-02-12 14:16:28 +01:00
Steffen Winter 5282acc149
fix: Change bad link to old rocm repository 2024-02-12 13:20:20 +01:00
aristocratos 9c34ac75dc v1.3.1 Bug fixes 2024-02-11 18:32:27 +01:00
Jakob P. Liljenberg 0f224bb0e2
Merge pull request #756 from imwints/unix-duplicates 2024-02-11 18:02:52 +01:00
Jakob P. Liljenberg 65f3ade9b6
Merge branch 'main' into unix-duplicates 2024-02-11 17:54:00 +01:00
Jakob P. Liljenberg e8137674b0
Merge pull request #755 from imwints/bsd 2024-02-11 17:53:39 +01:00
Jakob P. Liljenberg 1d62896c9b
Merge pull request #753 from lcheylus/utf8-ctype 2024-02-11 17:51:43 +01:00
Jakob P. Liljenberg 283ad3e76e
Merge branch 'main' into utf8-ctype 2024-02-11 17:49:35 +01:00
Jakob P. Liljenberg 97e78ebb12
Merge pull request #722 from MartinPit/hot-reload 2024-02-11 17:49:11 +01:00
aristocratos 1670e1db79 Reuse code from init, properly log warnings and move execution in to main loop 2024-02-11 17:42:51 +01:00
Jakob P. Liljenberg 67561d1994
Merge branch 'main' into hot-reload 2024-02-11 17:07:06 +01:00
Jakob P. Liljenberg 46f6b4fe90
Merge pull request #747 from aristocratos/fix/zombie 2024-02-11 17:06:23 +01:00
Jakob P. Liljenberg 459cbbeb52
Merge branch 'main' into fix/zombie 2024-02-11 16:49:49 +01:00
Jakob P. Liljenberg d460fc63dc
Merge pull request #746 from M-Sviridov/main 2024-02-11 16:49:25 +01:00
Jakob P. Liljenberg c587c9f1e3
Merge pull request #743 from planet36/config-trailing-newline 2024-02-11 16:46:44 +01:00
Jakob P. Liljenberg c7fdd8adfe
Merge branch 'main' into config-trailing-newline 2024-02-11 16:45:56 +01:00
Jakob P. Liljenberg 77c758c349
Merge pull request #689 from vsey/battery-power-2 2024-02-11 16:45:40 +01:00
Jakob P. Liljenberg f1f37ad6af
Merge branch 'main' into battery-power-2 2024-02-11 16:39:59 +01:00
Jakob P. Liljenberg 338aa72f6f
Merge pull request #735 from rkmcode/main 2024-02-11 16:33:46 +01:00
Jakob P. Liljenberg 842b9f83b2
Merge branch 'main' into main 2024-02-11 16:33:01 +01:00
Jakob P. Liljenberg cae6c86ecd
Merge pull request #720 from imwints/fmt-header-only 2024-02-11 16:21:17 +01:00
Jakob P. Liljenberg 7f5b060b0c
Merge branch 'main' into fmt-header-only 2024-02-11 16:11:52 +01:00
Jakob P. Liljenberg bf5618536b
Merge pull request #721 from imwints/debug 2024-02-11 16:11:32 +01:00
Jakob P. Liljenberg e0884917e6
Merge branch 'main' into debug 2024-02-11 16:11:05 +01:00
Jakob P. Liljenberg 1584ce6468
Merge pull request #717 from imwints/fix-716 2024-02-11 16:10:25 +01:00
Jakob P. Liljenberg 7057d7653d
Merge branch 'main' into fix-716 2024-02-11 15:58:38 +01:00
Jakob P. Liljenberg 91e137a411
Merge pull request #718 from imwints/cmake-openbsd 2024-02-11 15:58:08 +01:00
Jakob P. Liljenberg bb8c7bc35c
Merge branch 'main' into cmake-openbsd 2024-02-11 15:53:44 +01:00
Jakob P. Liljenberg 70dec20b23
Merge pull request #714 from tessus/fix/if-name-len 2024-02-11 15:51:49 +01:00
Jakob P. Liljenberg 8bf88c1918
Merge branch 'main' into fix/if-name-len 2024-02-11 15:50:14 +01:00
Steffen Winter ab0bef204a
collect: Share ifaddrs wrapper and use uniq_ptr-like syntax 2024-02-09 14:03:06 +01:00
Steffen Winter ee46dba838
bsd: Wrap kvm_t* in a uniq_ptr and share code between BSD's 2024-02-09 13:16:09 +01:00
Steffen Winter a0e2a5c1d2
cmake: Fix undefined reference to `kvm_openfiles' on BSD's 2024-02-09 12:06:16 +01:00
Laurent Cheylus f2ead3d3a9
Check LC_CTYPE to set UTF-8 locale
Fix aristocratos/btop#752

Signed-off-by: Laurent Cheylus <foxy@free.fr>
2024-02-08 14:35:21 +01:00
MartinPit 57703d3087
Merge branch 'main' into hot-reload 2024-02-05 16:08:57 +01:00
Jos Dehaes 2b09f29a1e fix: don't mangle memory for zombie processes
for a zombie process, `proc_pidpath` returns 0, and nothing is written in fullname, so it's uninitialized garbage
2024-02-02 09:28:07 +01:00
Mathieu Sviridov bc0eb4291f Add theme based on Everforest Dark Medium palette 2024-02-02 12:49:30 +11:00
Steven Ward 69363487bc Write newline at end of config file 2024-01-30 20:12:58 -05:00
vsey 0bb1d4bf97
Merge branch 'main' into battery-power-2 2024-01-30 22:05:00 +01:00
Jakob P. Liljenberg edcb68cbb9
Merge pull request #737 from fxzjshm/fix-rocm-v6
Fix dynamic loading of ROCm v6
2024-01-27 09:00:31 +01:00
fxzjshm 7d3617a274
Fix dynamic loading of ROCm v6
Corrected definition of `rsmi_frequencies_t` of ROCm v5 and v6.
Also added the missing `LOAD_SYM(rsmi_version_get);` as it is used later.

Fixes: 5511131 ("Support for dynamic loading of ROCm v6")
Signed-off-by: fxzjshm <fxzjshm@163.com>
2024-01-27 15:31:02 +08:00
aristocratos 4461a431ae Fixed incorrect used and available memory for OSX 2024-01-26 23:29:31 +01:00
aristocratos eab6c58137 Fix dependencies for Continuous Build Gpu 2024-01-26 22:48:04 +01:00
aristocratos 8019e117c7 Added continuous build for testing Gpu support 2024-01-26 22:45:11 +01:00
aristocratos 5511131572 Support for dynamic loading of ROCm v6 2024-01-26 22:11:23 +01:00
rliang 81d09860f7
Fix basic_string::_M_create exception
when 1000>hz>999.5, round(hz)=1000
btop_draw.cpp: 793: Symbols::h_line * (7 - cpuHz.size())  exception
2024-01-25 03:36:15 +08:00
Steffen Winter bdc8d0151d Ask for 'btop --version' in issue template 2024-01-24 15:02:14 +01:00
Steffen Winter 7717020197
Include build info in binary 2024-01-24 15:02:11 +01:00
jkre c750543950 Fix missing value in battery status tuple for openbsd 2024-01-22 22:32:16 +01:00
jkre 61105e46b7 Add battery power draw to battery inforamtion tuple for openbsd and set it to a constant 2024-01-22 22:20:33 +01:00
vsey 40cdb92b8e
Merge branch 'aristocratos:main' into battery-power-2 2024-01-22 22:01:14 +01:00
Martin Oliver Pitoňák fb994b69eb
added ctrl+r shortcut to reload config from disk 2024-01-17 17:27:18 +01:00
Martin Oliver Pitoňák e047f88bd5
SIGUSR2 signal now reloads the config 2024-01-17 16:41:58 +01:00
Steffen Winter 3174c83b43
-DFMT_HEADER_ONLY as a compiler flag
This just defines FMT_HEADER_ONLY everywhere instead of just in all
files that include `btop_tools.hpp`, in case the statement gets removed
there.
2024-01-17 09:56:18 +01:00
Martin Oliver Pitoňák 67a674e850
btop now reacts to SIGUSR1 by reloading config 2024-01-16 19:02:20 +01:00
Steffen Winter a44ce1c3a1
Make BTOP_DEBUG also work for CMake 2024-01-15 19:23:47 +01:00
Steffen Winter 57752df6fc
CMake: Enable OpenBSD 2024-01-15 16:07:24 +01:00
Steffen Winter cec251bf05
Allow the Findkvm module on all BSDs 2024-01-15 16:00:34 +01:00
Steffen Winter 05da55c549
Fix abort in locale detection on OpenBSD
For whatever reason catch doesn't work for exceptions thrown in
a dynamically linked library and the program aborts.
2024-01-15 15:55:04 +01:00
Helmut K. C. Tessarek 6a6f514f80 fix: increase interface name length to 15 2024-01-12 11:28:42 -05:00
Jakob P. Liljenberg b2df50396b
Update README.md -> Fixed bad links 2024-01-11 19:27:29 +01:00
aristocratos e936339038 Undefine FORTIFY_SOURCE before setting new value when enabled 2024-01-11 10:39:39 +01:00
Jakob P. Liljenberg c649369efb
Merge pull request #648 from imwints/fortification
Increase fortification level
2024-01-11 09:42:59 +01:00
Jakob P. Liljenberg 21fe2cc07b
Merge branch 'main' into fortification 2024-01-11 09:42:09 +01:00
Jakob P. Liljenberg d063cd300e
Merge pull request #711 from v4u6h4n/patch-1
Update README.md
2024-01-11 09:36:47 +01:00
aristocratos ca368c5b89 Added link to compile section 2024-01-11 09:35:20 +01:00
v4u6h4n 3cbb0484a4
Update README.md
Added optional dependencies to 'Prerequisites' section.
2024-01-11 12:19:09 +11:00
Jakob P. Liljenberg 60bd10d44c
Merge pull request #706 from imwints/cmake
Bump cmake to v1.3.0
2024-01-09 08:12:51 +01:00
Steffen Winter 19c6099c7c
Use _FORTIFY_SOURCE=3 and put it behind a build flag 2024-01-08 13:19:16 +01:00
Steffen Winter 4ab43fd159
Bump cmake to v1.3.0 2024-01-07 18:59:21 +01:00
vsey b28c5ffc40
Merge branch 'main' into battery-power-2 2024-01-03 20:52:30 +01:00
vsey fb6af5ddb4
Merge branch 'aristocratos:main' into battery-power-2 2023-12-29 01:14:34 +01:00
vsey 63ce0abc64
Merge branch 'aristocratos:main' into battery-power-2 2023-12-26 23:43:14 +01:00
vsey 9dd43796fd
Merge branch 'main' into battery-power-2 2023-12-25 12:32:01 +01:00
vsey 5792216eb9
Merge branch 'aristocratos:main' into battery-power-2 2023-12-17 21:19:39 +01:00
vsey 46743abab8
Merge branch 'main' into battery-power-2 2023-12-17 15:36:27 +01:00
jkre 0c706cd20a make os compatible 2023-12-15 01:28:57 +01:00
jkre a81b514d6d add freebsd support for battery power 2023-12-15 01:14:47 +01:00
jkre cd6c1b7294 make discribtion in menu and settings clearer 2023-12-14 23:27:19 +01:00
jkre 2934138a66 Only redraw battery indicator on power change if power change option is set to true 2023-12-14 22:56:31 +01:00
jkre 578b01e06b add show_battery_power option to menu 2023-12-14 22:19:22 +01:00
jkre 7a188bfaaf round wattage to second decimal 2023-12-14 01:39:00 +01:00
jkre 1ad1418771 remove redundant space 2023-12-14 00:58:17 +01:00
jkre ddd4bec1c3 Show wattage next to battery remaining time when wattage could be calculated 2023-12-14 00:54:29 +01:00
jkre 6e575116fe add power to get_battery function output 2023-12-14 00:53:01 +01:00
jkre 419a7d4ca3 add power draw calculation for battery 2023-12-14 00:32:06 +01:00
jkre b09f352c09 clean up if statement for battery percent calculation 2023-12-14 00:16:15 +01:00
jkre f6d8c4a044 use capacity as default for battery percentage, less complicated and matches desktop percent exactly 2023-12-13 23:58:40 +01:00
jkre ab294bfc10 add battery percentage calculation in charge case 2023-12-13 23:51:18 +01:00
jkre ee61700a44 add case of calculating the remaining battery time for current/charge 2023-12-13 23:39:45 +01:00
jkre b99008f626 Introduce charge in addition to energy for laptops that use charge instead of energy, this is done so that the units make more sense in this case 2023-12-13 23:17:07 +01:00
jkre 4c74a7c51d Add current_now and voltage_now to battery struct and fix naming of
current_now
2023-12-13 22:51:40 +01:00
56 changed files with 1004 additions and 327 deletions

View file

@ -28,10 +28,9 @@ Any bug that can be solved by just reading the [prerequisites](https://github.co
[If applicable, add screenshots to help explain your problem.]
**Info (please complete the following information):**
- btop++ version: `btop -v`
- btop++ version: `btop --version`
- If using snap: `snap info btop`
- Binary: [self compiled or static binary from release]
- (If compiled) Compiler and version:
- Architecture: [x86_64, aarch64, etc.] `uname -m`
- Platform: [Linux, FreeBSD, OsX]
- (Linux) Kernel: `uname -r`

View file

@ -33,8 +33,7 @@ jobs:
with:
release: '14.0'
usesh: true
prepare: pkg install -y cmake ninja
prepare: pkg install -y cmake ninja lowdown
run: |
CXX=clang++ cmake -B build -G Ninja -DBTOP_STATIC=ON
cmake --build build --verbose

View file

@ -30,11 +30,10 @@ jobs:
- uses: actions/checkout@v4
- name: Install build tools
run: apk add --no-cache --update clang cmake lld ninja
run: apk add --no-cache --update clang cmake lld ninja lowdown
- name: Configure
run: CXX=clang++ LDFLAGS=-fuse-ld=lld cmake -B build -G Ninja -DBTOP_STATIC=ON
- name: Compile
run: cmake --build build --verbose

View file

@ -32,7 +32,7 @@ jobs:
run: |
export HOMEBREW_NO_INSTALLED_DEPENDENTS_CHECK=1
brew update --quiet
brew install --force --overwrite cmake llvm@17 ninja
brew install --force --overwrite cmake llvm ninja lowdown
- name: Configure
run: |
@ -44,4 +44,3 @@ jobs:
- name: Compile
run: cmake --build build --verbose

View file

@ -45,7 +45,7 @@ jobs:
release: '14.0'
usesh: true
prepare: |
pkg install -y gmake gcc coreutils git
pkg install -y gmake gcc coreutils git lowdown
git config --global --add safe.directory /home/runner/work/btop/btop
run: |
CXX=${{ matrix.compiler }} gmake STATIC=true STRIP=true
@ -59,4 +59,3 @@ jobs:
name: btop-x86_64-freebsd-14
path: 'bin/*'
if-no-files-found: error

View file

@ -0,0 +1,45 @@
name: Continuous Build Gpu
on:
workflow_dispatch:
push:
branches:
- main
tags-ignore:
- '*.*'
paths:
- 'src/**'
- '!src/osx/**'
- '!src/freebsd/**'
- '!src/openbsd/**'
- 'include/**'
- 'Makefile'
- '.github/workflows/continuous-build-gpu.yml'
pull_request:
branches:
- main
paths:
- 'src/**'
- '!src/osx/**'
- '!src/freebsd/**'
- '!src/openbsd/**'
- 'include/**'
- 'Makefile'
- '.github/workflows/continuous-build-gpu.yml'
jobs:
gpu_build_linux:
runs-on: ubuntu-latest
container: alpine:edge
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
cancel-in-progress: true
steps:
- uses: actions/checkout@v4
- name: Install build tools
run: apk add --no-cache --update gcc g++ make
- name: Compile
run: make CXX=g++ GPU_SUPPORT=true

View file

@ -42,7 +42,7 @@ jobs:
release: '7.4'
usesh: true
prepare: |
pkg_add gmake gcc%11 g++%11 coreutils git
pkg_add gmake gcc%11 g++%11 coreutils git lowdown
git config --global --add safe.directory /home/runner/work/btop/btop
run: |
gmake CXX=eg++ STATIC=true STRIP=true
@ -55,4 +55,3 @@ jobs:
name: btop-x86_64-openbsd-7.4
path: 'bin/*'
if-no-files-found: error

View file

@ -1,5 +1,4 @@
name: 🧪 Test snap can be built on x86_64
on:
workflow_dispatch:
push:
@ -28,7 +27,7 @@ jobs:
runs-on: ubuntu-latest
strategy:
matrix:
node-version: [16.x]
node-version: [20.x]
steps:
- uses: actions/checkout@v2

5
.gitignore vendored
View file

@ -46,9 +46,14 @@ stage/
*.out
*.app
# Compiled man page
btop.1
build
bin
btop
/obj/
config.h
.*/
# Optional libraries

View file

@ -1,3 +1,25 @@
## v1.3.2
Description | Author(s) | References
--- | --- | ---
fix: Can't detect librocm 6.0.x | @imwints, @aristocratos | #761
## v1.3.1
Description | Author(s) | References
--- | --- | ---
GPU: Added support for dynamic loading of ROCm v6 libraries | @aristocratos, @fxzjshm | 5511131, #737
Increase max network interface name to 15 | @tessus | #714
Fix OpenBSD UTF-8 locale detection | @lcheylus, @imwints | #753, #717
Add hot-reloading of config file with CTRL+R or SIGUSR2 signal | @MartinPit | #722
Add battery power draw for linux and freebsd | @vsey | #689
Fix crash caused by string exception when cpu clock is exactly between 999.5 and 999.9 Mhz | @rkmcode | #735
Write newline at end of config file | @planet36 | #743
Add theme based on Everforest Dark Medium palette | @M-Sviridov | #746
fix: don't mangle memory for zombie processes | @joske | #747
Share common code from collect | @imwints | #756
Fixed incorrect used and available memory for OSX | | 4461a43
## v1.3.0
* Added Gpu Support Linux | @romner-set | PR #529
@ -158,7 +180,7 @@
* Fixed: Wrong memory unit when shorten and size is less than 10, by @mohi001
* Fixed: Use cpu cores avarage temp if missing cpu package temp for FreeBSD
* Fixed: Use cpu cores average temp if missing cpu package temp for FreeBSD
* Changed: Enter symbol to a more common variant
@ -454,7 +476,7 @@
* Fixed: Sizing constraints bug on start and boxes can be toggled from size error screen
* Fixed: UTF-8 check crashing if LANG was set to non existant locale
* Fixed: UTF-8 check crashing if LANG was set to non existent locale
## v1.0.4

View file

@ -11,7 +11,6 @@ if("${CMAKE_CURRENT_SOURCE_DIR}" STREQUAL "${CMAKE_CURRENT_BINARY_DIR}")
endif()
project("btop"
VERSION 1.2.13
DESCRIPTION "A monitor of resources"
HOMEPAGE_URL "https://github.com/aristocratos/btop"
LANGUAGES CXX
@ -41,6 +40,7 @@ option(BTOP_LTO "Enable LTO" ON)
option(BTOP_USE_MOLD "Use mold to link btop" OFF)
option(BTOP_PEDANTIC "Enable a bunch of additional warnings" OFF)
option(BTOP_WERROR "Compile with warnings as errors" OFF)
option(BTOP_FORTIFY "Detect buffer overflows with _FORTIFY_SOURCE=3" ON)
option(BTOP_GPU "Enable GPU support" ON)
cmake_dependent_option(BTOP_RSMI_STATIC "Link statically to ROCm SMI" OFF "BTOP_GPU" OFF)
@ -64,6 +64,8 @@ if(APPLE)
target_sources(btop PRIVATE src/osx/btop_collect.cpp src/osx/sensors.cpp src/osx/smc.cpp)
elseif(CMAKE_SYSTEM_NAME STREQUAL "FreeBSD")
target_sources(btop PRIVATE src/freebsd/btop_collect.cpp)
elseif(CMAKE_SYSTEM_NAME STREQUAL "OpenBSD")
target_sources(btop PRIVATE src/openbsd/btop_collect.cpp src/openbsd/sysctlbyname.cpp)
elseif(LINUX)
target_sources(btop PRIVATE src/linux/btop_collect.cpp)
else()
@ -75,6 +77,21 @@ if(NOT CXX_HAVE_RANGES)
message(FATAL_ERROR "The compiler doesn't support <ranges>")
endif()
# Generate build info
execute_process(
COMMAND "git" "rev-parse" "--short" "HEAD"
WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}"
OUTPUT_VARIABLE GIT_COMMIT
OUTPUT_STRIP_TRAILING_WHITESPACE ERROR_QUIET)
set(CONFIGURE_COMMAND
"cmake -DBTOP_STATIC=${BTOP_STATIC} -DBTOP_USE_MOLD=${BTOP_USE_MOLD} -DBTOP_FORTIFY=${BTOP_FORTIFY} -DBTOP_GPU=${BTOP_GPU}"
)
get_filename_component(CXX_COMPILER_BASENAME "${CMAKE_CXX_COMPILER}" NAME)
set(COMPILER "${CXX_COMPILER_BASENAME}")
set(COMPILER_VERSION "${CMAKE_CXX_COMPILER_VERSION}")
configure_file(${CMAKE_CURRENT_SOURCE_DIR}/src/config.h.in ${CMAKE_CURRENT_BINARY_DIR}/config.h @ONLY IMMEDIATE)
set(CMAKE_INCLUDE_CURRENT_DIR ON)
# Check for and enable LTO
check_ipo_supported(RESULT ipo_supported)
if(ipo_supported AND BTOP_LTO)
@ -97,7 +114,7 @@ if(BTOP_WERROR)
endif()
if(NOT APPLE)
target_compile_options(btop PRIVATE -fstack-clash-protection)
target_compile_options(btop PRIVATE -fstack-clash-protection)
endif()
check_cxx_compiler_flag(-fstack-protector HAS_FSTACK_PROTECTOR)
if(HAS_FSTACK_PROTECTOR)
@ -109,10 +126,11 @@ if(HAS_FCF_PROTECTION)
endif()
target_compile_definitions(btop PRIVATE
FMT_HEADER_ONLY
_FILE_OFFSET_BITS=64
$<$<CONFIG:Debug>:_GLIBCXX_ASSERTIONS _LIBCPP_ENABLE_ASSERTIONS=1>
# Only has an effect with optimizations enabled
$<$<NOT:$<CONFIG:Debug>>:_FORTIFY_SOURCE=2>
$<$<AND:$<NOT:$<CONFIG:Debug>>,$<BOOL:${BTOP_FORTIFY}>>:_FORTIFY_SOURCE=3>
)
target_include_directories(btop SYSTEM PRIVATE include)
@ -129,7 +147,7 @@ if(LINUX AND BTOP_GPU)
if(BTOP_RSMI_STATIC)
# ROCm doesn't properly add it's folders to the module path if `CMAKE_MODULE_PATH` is already
# set
# We could also manully append ROCm's path here
# We could also manually append ROCm's path here
set(_CMAKE_MODULE_PATH CMAKE_MODULE_PATH)
unset(CMAKE_MODULE_PATH)
@ -175,15 +193,43 @@ elseif(CMAKE_SYSTEM_NAME STREQUAL "FreeBSD")
INSTALL_RPATH "/usr/local/lib/gcc${GCC_VERSION_MAJOR}"
BUILD_WITH_INSTALL_RPATH TRUE
)
# The gcc compiler wrapper doesn't add '--eh-frame-hdr' on FreeBSD with static builds
# https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=278551
if(BTOP_STATIC)
target_link_options(btop PRIVATE LINKER:--eh-frame-hdr)
endif()
endif()
find_package(devstat REQUIRED)
target_link_libraries(btop devstat::devstat)
find_package(kvm REQUIRED)
target_link_libraries(btop devstat::devstat kvm::kvm)
if(BTOP_STATIC)
find_package(elf REQUIRED)
find_package(kvm REQUIRED)
target_link_libraries(btop elf::elf kvm::kvm)
target_link_libraries(btop elf::elf)
endif()
elseif(CMAKE_SYSTEM_NAME STREQUAL "OpenBSD")
if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
target_compile_options(btop PRIVATE -static-libstdc++)
endif()
find_package(kvm REQUIRED)
target_link_libraries(btop kvm::kvm)
endif()
# Check if lowdown is installed
find_program(LOWDOWN_EXECUTABLE lowdown)
if(LOWDOWN_EXECUTABLE)
# Custom target to compile Markdown to man page using lowdown
add_custom_target(btop.1 ALL
COMMAND lowdown -s -Tman -o btop.1 manpage.md
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
)
# Install the man page
install(FILES btop.1 DESTINATION "share/man/man1")
else()
message(WARNING "Command 'lowdown' not found: skipping generating man page btop.1")
endif()
install(TARGETS btop RUNTIME)
@ -191,4 +237,3 @@ install(FILES "btop.desktop" DESTINATION "share/applications")
install(FILES "Img/icon.png" DESTINATION "share/icons/hicolor/48x48/apps" RENAME "btop.png")
install(FILES "Img/icon.svg" DESTINATION "share/icons/hicolor/scalable/apps" RENAME "btop.svg")
install(DIRECTORY "themes" DESTINATION "share/btop")

View file

@ -50,6 +50,11 @@ ifeq ($(GPU_SUPPORT),true)
override ADDFLAGS += -DGPU_SUPPORT
endif
FORTIFY_SOURCE ?= true
ifeq ($(FORTIFY_SOURCE),true)
override ADDFLAGS += -U_FORTIFY_SOURCE -D_FORTIFY_SOURCE=3
endif
#? Compiler and Linker
ifeq ($(shell $(CXX) --version | grep clang >/dev/null 2>&1; echo $$?),0)
override CXX_IS_CLANG := true
@ -92,17 +97,18 @@ ifneq ($(PLATFORM) $(ARCH),macos arm64)
endif
ifeq ($(STATIC),true)
ifeq ($(CXX_IS_CLANG) $(CLANG_WORKS),true true)
ifeq ($(CXX_IS_CLANG),true)
ifeq ($(shell $(CXX) -print-target-triple | grep gnu >/dev/null; echo $$?),0)
$(error $(shell printf "\033[1;91mERROR: \033[97m$(CXX) can't statically link glibc\033[0m"))
endif
else
override ADDFLAGS += -static-libgcc -static-libstdc++
endif
ifeq ($(PLATFORM_LC),linux)
override ADDFLAGS += -DSTATIC_BUILD -static -Wl,--fatal-warnings
else ifeq ($(PLATFORM_LC),freebsd)
override ADDFLAGS += -DSTATIC_BUILD
ifeq ($(PLATFORM_LC),$(filter $(PLATFORM_LC),freebsd linux))
override ADDFLAGS += -DSTATIC_BUILD -static
else
ifeq ($(CXX_IS_CLANG),false)
override ADDFLAGS += -static-libgcc -static-libstdc++
endif
endif
endif
@ -125,9 +131,13 @@ else ifeq ($(PLATFORM_LC),freebsd)
PLATFORM_DIR := freebsd
THREADS := $(shell getconf NPROCESSORS_ONLN 2>/dev/null || echo 1)
SU_GROUP := wheel
override ADDFLAGS += -lm -lkvm -ldevstat -Wl,-rpath=/usr/local/lib/gcc$(CXX_VERSION_MAJOR)
ifneq ($(STATIC),true)
override ADDFLAGS += -lstdc++
override ADDFLAGS += -lm -lkvm -ldevstat
ifeq ($(STATIC),true)
override ADDFLAGS += -lelf -Wl,--eh-frame-hdr
endif
ifeq ($(CXX_IS_CLANG),false)
override ADDFLAGS += -lstdc++ -Wl,rpath=/usr/local/lib/gcc$(CXX_VERSION_MAJOR)
endif
export MAKE = gmake
else ifeq ($(PLATFORM_LC),macos)
@ -138,7 +148,7 @@ else ifeq ($(PLATFORM_LC),macos)
else ifeq ($(PLATFORM_LC),openbsd)
PLATFORM_DIR := openbsd
THREADS := $(shell sysctl -n hw.ncpu || echo 1)
override ADDFLAGS += -lkvm
override ADDFLAGS += -lkvm -static-libstdc++
export MAKE = gmake
SU_GROUP := wheel
else
@ -158,6 +168,12 @@ else
LTO := $(THREADS)
endif
GIT_COMMIT := $(shell git rev-parse --short HEAD 2> /dev/null || true)
CONFIGURE_COMMAND := $(MAKE) STATIC=$(STATIC) FORTIFY_SOURCE=$(FORTIFY_SOURCE)
ifeq ($(PLATFORM_LC),linux)
CONFIGURE_COMMAND += GPU_SUPPORT=$(GPU_SUPPORT) RSMI_STATIC=$(RSMI_STATIC)
endif
#? The Directories, Source, Includes, Objects and Binary
SRCDIR := src
INCDIRS := include $(wildcard lib/**/include)
@ -174,10 +190,10 @@ override GOODFLAGS := $(foreach flag,$(TESTFLAGS),$(strip $(shell echo "int main
override REQFLAGS := -std=c++20
WARNFLAGS := -Wall -Wextra -pedantic
OPTFLAGS := -O2 -ftree-vectorize -flto=$(LTO)
LDCXXFLAGS := -pthread -D_FORTIFY_SOURCE=2 -D_GLIBCXX_ASSERTIONS -D_FILE_OFFSET_BITS=64 $(GOODFLAGS) $(ADDFLAGS)
LDCXXFLAGS := -pthread -DFMT_HEADER_ONLY -D_GLIBCXX_ASSERTIONS -D_FILE_OFFSET_BITS=64 $(GOODFLAGS) $(ADDFLAGS)
override CXXFLAGS += $(REQFLAGS) $(LDCXXFLAGS) $(OPTFLAGS) $(WARNFLAGS)
override LDFLAGS += $(LDCXXFLAGS) $(OPTFLAGS) $(WARNFLAGS)
INC := $(foreach incdir,$(INCDIRS),-isystem $(incdir)) -I$(SRCDIR)
INC := $(foreach incdir,$(INCDIRS),-isystem $(incdir)) -I$(SRCDIR) -I$(BUILDDIR)
SU_USER := root
ifdef DEBUG
@ -217,7 +233,7 @@ endif
#? Default Make
.ONESHELL:
all: | info rocm_smi info-quiet directories btop
all: | info rocm_smi info-quiet directories btop.1 config.h btop
ifneq ($(QUIET),true)
info:
@ -238,7 +254,6 @@ info:
@true
endif
info-quiet: | info rocm_smi
@printf "\n\033[1;92mBuilding btop++ \033[91m(\033[97mv$(BTOP_VERSION)\033[91m) \033[93m$(PLATFORM) \033[96m$(ARCH)\033[0m\n"
@ -262,6 +277,22 @@ directories:
@$(VERBOSE) || printf "mkdir -p $(BUILDDIR)/$(PLATFORM_DIR)\n"
@mkdir -p $(BUILDDIR)/$(PLATFORM_DIR)
config.h: $(BUILDDIR)/config.h
$(BUILDDIR)/config.h: $(SRCDIR)/config.h.in | directories
@$(QUIET) || printf "\033[1mConfiguring $(BUILDDIR)/config.h\033[0m\n"
@$(VERBOSE) || printf 'sed -e "s|@GIT_COMMIT@|$(GIT_COMMIT)|" -e "s|@CONFIGURE_COMMAND@|$(CONFIGURE_COMMAND)|" -e "s|@COMPILER@|$(CXX)|" -e "s|@COMPILER_VERSION@|$(CXX_VERSION)|" $< | tee $@ > /dev/null\n'
@sed -e "s|@GIT_COMMIT@|$(GIT_COMMIT)|" -e "s|@CONFIGURE_COMMAND@|$(CONFIGURE_COMMAND)|" -e "s|@COMPILER@|$(CXX)|" -e "s|@COMPILER_VERSION@|$(CXX_VERSION)|" $< | tee $@ > /dev/null
#? Man page
btop.1: manpage.md | directories
ifeq ($(shell command -v lowdown >/dev/null; echo $$?),0)
@printf "\n\033[1;92mGenerating man page $@\033[37m...\033[0m\n"
lowdown -s -Tman -o $@ $<
else
@printf "\n\033[1;93mCommand 'lowdown' not found: skipping generating man page $@\033[0m\n"
endif
#? Clean only Objects
clean:
@printf "\033[1;91mRemoving: \033[1;97mbuilt objects...\033[0m\n"
@ -293,7 +324,11 @@ install:
@printf "\033[1;92mInstalling SVG icon to: \033[1;97m$(DESTDIR)$(PREFIX)/share/icons/hicolor/scalable/apps/btop.svg\n"
@mkdir -p $(DESTDIR)$(PREFIX)/share/icons/hicolor/scalable/apps
@cp -p Img/icon.svg $(DESTDIR)$(PREFIX)/share/icons/hicolor/scalable/apps/btop.svg
ifneq ($(wildcard btop.1),)
@printf "\033[1;92mInstalling man page to: \033[1;97m$(DESTDIR)$(PREFIX)/share/man/man1/btop.1\n"
@mkdir -p $(DESTDIR)$(PREFIX)/share/man/man1
@cp -p btop.1 $(DESTDIR)$(PREFIX)/share/man/man1/btop.1
endif
#? Set SUID bit for btop as $SU_USER in $SU_GROUP
setuid:
@ -303,17 +338,20 @@ setuid:
@printf "\033[1;92mSetting SUID bit\033[0m\n"
@chmod u+s $(DESTDIR)$(PREFIX)/bin/btop
# With 'rm -v' user will see what files (if any) got removed
uninstall:
@printf "\033[1;91mRemoving: \033[1;97m$(DESTDIR)$(PREFIX)/bin/btop\033[0m\n"
@rm -rf $(DESTDIR)$(PREFIX)/bin/btop
@rm -rfv $(DESTDIR)$(PREFIX)/bin/btop
@printf "\033[1;91mRemoving: \033[1;97m$(DESTDIR)$(PREFIX)/share/btop\033[0m\n"
@rm -rf $(DESTDIR)$(PREFIX)/share/btop
@rm -rfv $(DESTDIR)$(PREFIX)/share/btop
@printf "\033[1;91mRemoving: \033[1;97m$(DESTDIR)$(PREFIX)/share/applications/btop.desktop\033[0m\n"
@rm -rf $(DESTDIR)$(PREFIX)/share/applications/btop.desktop
@rm -rfv $(DESTDIR)$(PREFIX)/share/applications/btop.desktop
@printf "\033[1;91mRemoving: \033[1;97m$(DESTDIR)$(PREFIX)/share/icons/hicolor/48x48/apps/btop.png\033[0m\n"
@rm -rf $(DESTDIR)$(PREFIX)/share/icons/hicolor/48x48/apps/btop.png
@rm -rfv $(DESTDIR)$(PREFIX)/share/icons/hicolor/48x48/apps/btop.png
@printf "\033[1;91mRemoving: \033[1;97m$(DESTDIR)$(PREFIX)/share/icons/hicolor/scalable/apps/btop.svg\033[0m\n"
@rm -rf $(DESTDIR)$(PREFIX)/share/icons/hicolor/scalable/apps/btop.svg
@rm -rfv $(DESTDIR)$(PREFIX)/share/icons/hicolor/scalable/apps/btop.svg
@printf "\033[1;91mRemoving: \033[1;97m$(DESTDIR)$(PREFIX)/share/man/man1/btop.1\033[0m\n"
@rm -rfv $(DESTDIR)$(PREFIX)/share/man/man1/btop.1
#? Pull in dependency info for *existing* .o files
-include $(OBJECTS:.$(OBJEXT)=.$(DEPEXT))
@ -357,7 +395,7 @@ btop: $(OBJECTS) | rocm_smi directories
#? Compile
.ONESHELL:
$(BUILDDIR)/%.$(OBJEXT): $(SRCDIR)/%.$(SRCEXT) | rocm_smi directories
$(BUILDDIR)/%.$(OBJEXT): $(SRCDIR)/%.$(SRCEXT) | rocm_smi directories config.h
@sleep 0.3 2>/dev/null || true
@TSTAMP=$$(date +%s 2>/dev/null || echo "0")
@$(QUIET) || printf "\033[1;97mCompiling $<\033[0m\n"
@ -366,4 +404,4 @@ $(BUILDDIR)/%.$(OBJEXT): $(SRCDIR)/%.$(SRCEXT) | rocm_smi directories
@printf "\033[1;92m$$($(PROGRESS))$(P)\033[10D\033[5C-> \033[1;37m$@ \033[100D\033[38C\033[1;93m(\033[1;97m$$(du -ah $@ | cut -f1)iB\033[1;93m) \033[92m(\033[97m$$($(DATE_CMD) -d @$$(expr $$($(DATE_CMD) +%s 2>/dev/null || echo "0") - $${TSTAMP} 2>/dev/null) -u +%Mm:%Ss 2>/dev/null | sed 's/^00m://' || echo '')\033[92m)\033[0m\n"
#? Non-File Targets
.PHONY: all msg help pre
.PHONY: all config.h msg help pre

133
README.md
View file

@ -47,8 +47,8 @@
Btop release v1.3.0
Big release with GPU support added for Linux and platform support for OpenBSD. Big thanks to @romner-set (GPU support) and @joske (OpenBSD support) for contributions.
And a multitude of bugfixes and small changes, see [CHANGES.md](CHANGES.md) and latest [release](https://github.com/aristocratos/btop/releases/latest) for detailed list and attributions.
Big release with GPU support added for Linux and platform support for OpenBSD. Big thanks to [@romner-set](https://github.com/romner-set) (GPU support) and [@joske](https://github.com/joske) (OpenBSD support) for contributions.
And a multitude of bugfixes and small changes, see [CHANGELOG.md](CHANGELOG.md) and latest [release](https://github.com/aristocratos/btop/releases/latest) for detailed list and attributions.
See news entry below for more information regarding GPU support.
@ -106,7 +106,7 @@ If you want to help out, test for bugs/fix bugs or just try out the branches:
**macOS / OSX**
```bash
# Install and use Homebrew or MacPorts package managers for easy dependency installation
brew install coreutils make gcc@11
brew install coreutils make gcc@11 lowdown
git clone https://github.com/aristocratos/btop.git
cd btop
git checkout OSX
@ -115,7 +115,7 @@ gmake
**FreeBSD**
```bash
sudo pkg install gmake gcc11 coreutils git
sudo pkg install gmake gcc11 coreutils git lowdown
git clone https://github.com/aristocratos/btop.git
cd btop
git checkout freebsd
@ -222,6 +222,22 @@ Also needs a UTF8 locale and a font that covers:
* Unicode Block “Geometric Shapes” U+25A0 - U+25FF
* Unicode Block "Box Drawing" and "Block Elements" U+2500 - U+259F
### **Optional Dependencies (Needed for GPU monitoring)**
GPU monitoring also requires a btop binary built with GPU support (`GPU_SUPPORT=true` flag).
See [GPU compatibility](#gpu-compatibility) section for more about compiling with GPU support.
* **NVIDIA**
If you have an NVIDIA GPU you must use an official NVIDIA driver, both the closed-source and open-source ones have been verified to work.
In addition to that you must also have the nvidia-ml dynamic library installed, which should be included with the driver package of your distribution.
* **AMD**
If you have an AMD GPU `rocm_smi_lib` is required, which may or may not be packaged for your distribution.
### **Notice (Text rendering issues)**
* If you are having problems with the characters in the graphs not looking like they do in the screenshots, it's likely a problem with your systems configured fallback font not having support for braille characters.
@ -362,12 +378,12 @@ Also needs a UTF8 locale and a font that covers:
* **AMD**
AMDGPU data is queried using the [ROCm SMI](https://github.com/RadeonOpenCompute/rocm_smi_lib) library, which may or may not be packaged for your distribution. If your distribution doesn't provide a package, btop++ is statically linked to ROCm SMI with the `RSMI_STATIC=true` make flag.
AMDGPU data is queried using the [ROCm SMI](https://github.com/rocm/rocm_smi_lib) library, which may or may not be packaged for your distribution. If your distribution doesn't provide a package, btop++ is statically linked to ROCm SMI with the `RSMI_STATIC=true` make flag.
This flag expects the ROCm SMI source code in `lib/rocm_smi_lib`, and compilation will fail if it's not there. The latest tested version is 5.6.x, which can be obtained with the following command:
```bash
git clone https://github.com/RadeonOpenCompute/rocm_smi_lib.git --depth 1 -b rocm-5.6.x lib/rocm_smi_lib
git clone https://github.com/rocm/rocm_smi_lib.git --depth 1 -b rocm-5.6.x lib/rocm_smi_lib
```
<details>
@ -379,7 +395,7 @@ Also needs a UTF8 locale and a font that covers:
1. **Install dependencies (example for Ubuntu 21.04 Hirsute)**
```bash
sudo apt install coreutils sed git build-essential gcc-11 g++-11
sudo apt install coreutils sed git build-essential gcc-11 g++-11 lowdown
```
2. **Clone repository**
@ -405,10 +421,11 @@ Also needs a UTF8 locale and a font that covers:
| `STRIP=true` | To force stripping of debug symbols (adds `-s` linker flag) |
| `DEBUG=true` | Sets OPTFLAGS to `-O0 -g` and enables more verbose debug logging |
| `ARCH=<architecture>` | To manually set the target architecture |
| `FORTIFY_SOURCE=false` | Disable fortification with `_FORTIFY_SOURCE=3` |
| `GPU_SUPPORT=<true\|false>` | Enable/disable GPU support (Enabled by default on X86_64 Linux) |
| `RSMI_STATIC=true` | To statically link the ROCm SMI library used for querying AMDGPU |
| `ADDFLAGS=<flags>` | For appending flags to both compiler and linker |
| `CXX=<compiler>` | Manualy set which compiler to use |
| `CXX=<compiler>` | Manually set which compiler to use |
Example: `make ADDFLAGS=-march=native` might give a performance boost if compiling only for your own system.
@ -469,12 +486,12 @@ Also needs a UTF8 locale and a font that covers:
1. **Install build dependencies**
Requires Clang / GCC, CMake, Ninja and Git
Requires Clang / GCC, CMake, Ninja, Lowdown and Git
For example, with Debian Bookworm:
```bash
sudo apt install cmake git g++ ninja-build
sudo apt install cmake git g++ ninja-build lowdown
```
2. **Clone the repository**
@ -503,6 +520,7 @@ Also needs a UTF8 locale and a font that covers:
| `-DBTOP_USE_MOLD=<ON\|OFF>` | Use mold to link btop (OFF by default) |
| `-DBTOP_PEDANTIC=<ON\|OFF>` | Compile with additional warnings (OFF by default) |
| `-DBTOP_WERROR=<ON\|OFF>` | Compile with warnings as errors (OFF by default) |
| `-DBTOP_FORTIFY=<ON\|OFF>` | Detect buffer overflows with `_FORTIFY_SOURCE=3` (ON by default) |
| `-DBTOP_GPU=<ON\|OFF>` | Enable GPU support (ON by default) |
| `-DBTOP_RSMI_STATIC=<ON\|OFF>` | Build and link the ROCm SMI library statically (OFF by default) |
| `-DCMAKE_INSTALL_PREFIX=<path>` | The installation prefix ('/usr/local' by default) |
@ -551,7 +569,7 @@ Also needs a UTF8 locale and a font that covers:
1. **Install dependencies (example for Homebrew)**
```bash
brew install coreutils make gcc@12
brew install coreutils make gcc@12 lowdown
```
2. **Clone repository**
@ -576,8 +594,9 @@ Also needs a UTF8 locale and a font that covers:
| `STRIP=true` | To force stripping of debug symbols (adds `-s` linker flag) |
| `DEBUG=true` | Sets OPTFLAGS to `-O0 -g` and enables more verbose debug logging |
| `ARCH=<architecture>` | To manually set the target architecture |
| `FORTIFY_SOURCE=false` | Disable fortification with `_FORTIFY_SOURCE=3` |
| `ADDFLAGS=<flags>` | For appending flags to both compiler and linker |
| `CXX=<compiler>` | Manualy set which compiler to use |
| `CXX=<compiler>` | Manually set which compiler to use |
Example: `gmake ADDFLAGS=-march=native` might give a performance boost if compiling only for your own system.
@ -636,11 +655,11 @@ Also needs a UTF8 locale and a font that covers:
1. **Install build dependencies**
Requires Clang, CMake, Ninja and Git
Requires Clang, CMake, Ninja, Lowdown and Git
```bash
brew update --quiet
brew install cmake git llvm ninja
brew install cmake git llvm ninja lowdown
```
2. **Clone the repository**
@ -674,6 +693,7 @@ Also needs a UTF8 locale and a font that covers:
| `-DBTOP_USE_MOLD=<ON\|OFF>` | Use mold to link btop (OFF by default) |
| `-DBTOP_PEDANTIC=<ON\|OFF>` | Compile with additional warnings (OFF by default) |
| `-DBTOP_WERROR=<ON\|OFF>` | Compile with warnings as errors (OFF by default) |
| `-DBTOP_FORTIFY=<ON\|OFF>` | Detect buffer overflows with `_FORTIFY_SOURCE=3` (ON by default) |
| `-DCMAKE_INSTALL_PREFIX=<path>` | The installation prefix ('/usr/local' by default) |
To force any specific compiler, run `CXX=<compiler> cmake -B build -G Ninja`
@ -716,7 +736,7 @@ Also needs a UTF8 locale and a font that covers:
1. **Install dependencies**
```bash
sudo pkg install gmake gcc11 coreutils git
sudo pkg install gmake gcc11 coreutils git lowdown
```
2. **Clone repository**
@ -742,8 +762,9 @@ Also needs a UTF8 locale and a font that covers:
| `STRIP=true` | To force stripping of debug symbols (adds `-s` linker flag) |
| `DEBUG=true` | Sets OPTFLAGS to `-O0 -g` and enables more verbose debug logging |
| `ARCH=<architecture>` | To manually set the target architecture |
| `FORTIFY_SOURCE=false` | Disable fortification with `_FORTIFY_SOURCE=3` |
| `ADDFLAGS=<flags>` | For appending flags to both compiler and linker |
| `CXX=<compiler>` | Manualy set which compiler to use |
| `CXX=<compiler>` | Manually set which compiler to use |
Example: `gmake ADDFLAGS=-march=native` might give a performance boost if compiling only for your own system.
@ -802,18 +823,18 @@ Also needs a UTF8 locale and a font that covers:
1. **Install build dependencies**
Requires Clang / GCC, CMake, Ninja and Git
Requires Clang / GCC, CMake, Ninja, Lowdown and Git
_**Note:** LLVM's libc++ shipped with FreeBSD 13 is too old and cannot compile btop._
FreeBSD 14 and later:
```bash
pkg install cmake ninja
pkg install cmake ninja lowdown
```
FreeBSD 13:
```bash
pkg install cmake gcc13 ninja
pkg install cmake gcc13 ninja lowdown
```
2. **Clone the repository**
@ -851,6 +872,7 @@ Also needs a UTF8 locale and a font that covers:
| `-DBTOP_USE_MOLD=<ON\|OFF>` | Use mold to link btop (OFF by default) |
| `-DBTOP_PEDANTIC=<ON\|OFF>` | Compile with additional warnings (OFF by default) |
| `-DBTOP_WERROR=<ON\|OFF>` | Compile with warnings as errors (OFF by default) |
| `-DBTOP_FORTIFY=<ON\|OFF>` | Detect buffer overflows with `_FORTIFY_SOURCE=3` (ON by default) |
| `-DCMAKE_INSTALL_PREFIX=<path>` | The installation prefix ('/usr/local' by default) |
_**Note:** Static linking does not work with GCC._
@ -895,7 +917,7 @@ Also needs a UTF8 locale and a font that covers:
1. **Install dependencies**
```bash
pkg_add gmake gcc%11 g++%11 coreutils git
pkg_add gmake gcc%11 g++%11 coreutils git lowdown
```
2. **Clone repository**
@ -921,8 +943,9 @@ Also needs a UTF8 locale and a font that covers:
| `STRIP=true` | To force stripping of debug symbols (adds `-s` linker flag) |
| `DEBUG=true` | Sets OPTFLAGS to `-O0 -g` and enables more verbose debug logging |
| `ARCH=<architecture>` | To manually set the target architecture |
| `FORTIFY_SOURCE=false` | Disable fortification with `_FORTIFY_SOURCE=3` |
| `ADDFLAGS=<flags>` | For appending flags to both compiler and linker |
| `CXX=<compiler>` | Manualy set which compiler to use |
| `CXX=<compiler>` | Manually set which compiler to use |
Example: `gmake ADDFLAGS=-march=native` might give a performance boost if compiling only for your own system.
@ -972,6 +995,74 @@ Also needs a UTF8 locale and a font that covers:
gmake help
```
</details>
<details>
<summary>
### With CMake (Community maintained)
</summary>
1. **Install build dependencies**
Requires GCC, CMake, Ninja, Lowdown and Git
_**Note:** LLVM's libc++ shipped with OpenBSD 7.4 is too old and cannot compile btop._
```bash
pkg_add cmake g++%11 git ninja lowdown
```
2. **Clone the repository**
```bash
git clone https://github.com/aristocratos/btop.git && cd btop
```
3. **Compile**
```bash
# Configure
CXX=eg++ cmake -B build -G Ninja
# Build
cmake --build build
```
This will automatically build a release version of btop.
Some useful options to pass to the configure step:
| Configure flag | Description |
|---------------------------------|-------------------------------------------------------------------------|
| `-DBTOP_LTO=<ON\|OFF>` | Enables link time optimization (ON by default) |
| `-DBTOP_USE_MOLD=<ON\|OFF>` | Use mold to link btop (OFF by default) |
| `-DBTOP_PEDANTIC=<ON\|OFF>` | Compile with additional warnings (OFF by default) |
| `-DBTOP_WERROR=<ON\|OFF>` | Compile with warnings as errors (OFF by default) |
| `-DBTOP_FORTIFY=<ON\|OFF>` | Detect buffer overflows with `_FORTIFY_SOURCE=3` (ON by default) |
| `-DCMAKE_INSTALL_PREFIX=<path>` | The installation prefix ('/usr/local' by default) |
To force any other compiler, run `CXX=<compiler> cmake -B build -G Ninja`
4. **Install**
```bash
cmake --install build
```
May require root privileges
5. **Uninstall**
CMake doesn't generate an uninstall target by default. To remove installed files, run
```
cat build/install_manifest.txt | xargs rm -irv
```
6. **Cleanup build directory**
```bash
cmake --build build -t clean
```
</details>
## Installing the snap

View file

@ -3,7 +3,7 @@
# Find libkvm, the Kernel Data Access Library
#
if(CMAKE_SYSTEM_NAME STREQUAL "FreeBSD")
if(BSD)
find_path(kvm_INCLUDE_DIR NAMES kvm.h)
find_library(kvm_LIBRARY NAMES kvm)

57
manpage.md Normal file
View file

@ -0,0 +1,57 @@
% btop(1) | User Commands
%
% "January 4 2024"
# NAME
btop - Resource monitor that shows usage and stats for processor, memory, disks, network, and processes.
# SYNOPSIS
**btop** [**-lc**] [**-t** | **+t**] [**-p** _id_] [**\-\-utf-force**]
[**\-\-debug**] [{**-h** | **\-\-help**} | {**-v** | **\-\-version**}]
# DESCRIPTION
**btop** is a program that shows usage and stats for processor, memory, disks, network, and processes.
# OPTIONS
The program follows the usual GNU command line syntax, with long options
starting with two dashes ('-'). A summary of options is included below.
**-lc**, **\-\-low-color**
: Disable truecolor, converts 24-bit colors to 256-color.
**-t**, **\-\-tty_on**
: Force (ON) tty mode, max 16 colors and tty-friendly graph symbols.
**+t**, **\-\-tty_off**
: Force (OFF) tty mode.
**-p**, **\-\-preset _id_**
: Start with preset, integer value between 0-9.
**\-\-utf-force**
: Force start even if no UTF-8 locale was detected.
**\-\-debug**
: Start in DEBUG mode: shows microsecond timer for information collect and screen draw functions and sets loglevel to DEBUG.
**-h**, **\-\-help**
: Show summary of options.
**-v**, **\-\-version**
: Show version of program.
# BUGS
The upstream bug tracker can be found at https://github.com/aristocratos/btop/issues.
# SEE ALSO
**top**(1), **htop**(1)
# AUTHOR
**btop** was written by Jakob P. Liljenberg a.k.a. "Aristocratos".

View file

@ -6,7 +6,7 @@ description: |
C++ version and continuation of bashtop and bpytop.
license: Apache-2.0
base: core20
base: core22
grade: stable
confinement: strict
compression: lzo
@ -49,6 +49,8 @@ parts:
- PREFIX=/usr/local
- STATIC=true
- ADDFLAGS="-D SNAPPED"
# Add 'lowdown' to build dependencies as soon at Snap builder updates from
# Ubuntu 20.04 "Focal" to something newer that has Lowdown included
build-packages:
- coreutils
- sed
@ -56,7 +58,7 @@ parts:
- build-essential
- gcc-11
- g++-11
override-pull: |
snapcraftctl pull
snapcraftctl set-version "$(git describe --tags | sed 's/^v//' | cut -d "-" -f1)"

View file

@ -52,7 +52,9 @@ tab-size = 4
#include "btop_theme.hpp"
#include "btop_draw.hpp"
#include "btop_menu.hpp"
#include "config.h"
#include "fmt/core.h"
#include "fmt/ostream.h"
using std::atomic;
using std::cout;
@ -78,7 +80,7 @@ namespace Global {
{"#801414", "██████╔╝ ██║ ╚██████╔╝██║ ╚═╝ ╚═╝"},
{"#000000", "╚═════╝ ╚═╝ ╚═════╝ ╚═╝"},
};
const string Version = "1.3.0";
const string Version = "1.3.2";
int coreCount;
string overlay;
@ -108,6 +110,7 @@ namespace Global {
atomic<bool> should_sleep (false);
atomic<bool> _runner_started (false);
atomic<bool> init_conf (false);
atomic<bool> reload_conf (false);
bool arg_tty{};
bool arg_low_color{};
@ -115,6 +118,19 @@ namespace Global {
int arg_update = 0;
}
static void print_version() {
if constexpr (GIT_COMMIT.empty()) {
fmt::print("btop version: {}\n", Global::Version);
} else {
fmt::print("btop version: {}+{}\n", Global::Version, GIT_COMMIT);
}
}
static void print_version_with_build_info() {
print_version();
fmt::print("Compiled with: {} ({})\nConfigured with: {}\n", COMPILER, COMPILER_VERSION, CONFIGURE_COMMAND);
}
//* A simple argument parser
void argumentParser(const int argc, char **argv) {
for(int i = 1; i < argc; i++) {
@ -136,8 +152,12 @@ void argumentParser(const int argc, char **argv) {
);
exit(0);
}
else if (is_in(argument, "-v", "--version")) {
fmt::println("btop version: {}", Global::Version);
else if (is_in(argument, "-v")) {
print_version();
exit(0);
}
else if (is_in(argument, "--version")) {
print_version_with_build_info();
exit(0);
}
else if (is_in(argument, "-lc", "--low-color")) {
@ -364,9 +384,38 @@ void _signal_handler(const int sig) {
case SIGUSR1:
// Input::poll interrupt
break;
case SIGUSR2:
Global::reload_conf = true;
Input::interrupt();
break;
}
}
//* Config init
void init_config(){
atomic_lock lck(Global::init_conf);
vector<string> load_warnings;
Config::load(Config::conf_file, load_warnings);
Config::set("lowcolor", (Global::arg_low_color ? true : not Config::getB("truecolor")));
static bool first_init = true;
if (Global::debug and first_init) {
Logger::set("DEBUG");
Logger::debug("Running in DEBUG mode!");
}
else Logger::set(Config::getS("log_level"));
static string log_level;
if (const string current_level = Config::getS("log_level"); log_level != current_level) {
log_level = current_level;
Logger::info("Logger set to " + (Global::debug ? "DEBUG" : log_level));
}
for (const auto& err_str : load_warnings) Logger::warning(err_str);
first_init = false;
}
//* Manages secondary thread for collection and drawing of boxes
namespace Runner {
atomic<bool> active (false);
@ -403,7 +452,7 @@ namespace Runner {
}
};
//* Wrapper for raising priviliges when using SUID bit
//* Wrapper for raising privileges when using SUID bit
class gain_priv {
int status = -1;
public:
@ -836,7 +885,7 @@ int main(int argc, char **argv) {
Global::start_time = time_s();
//? Save real and effective userid's and drop priviliges until needed if running with SUID bit set
//? Save real and effective userid's and drop privileges until needed if running with SUID bit set
Global::real_uid = getuid();
Global::set_uid = geteuid();
if (Global::real_uid != Global::set_uid) {
@ -895,22 +944,7 @@ int main(int argc, char **argv) {
}
//? Config init
{
atomic_lock lck(Global::init_conf);
vector<string> load_warnings;
Config::load(Config::conf_file, load_warnings);
Config::set("lowcolor", (Global::arg_low_color ? true : not Config::getB("truecolor")));
if (Global::debug) {
Logger::set("DEBUG");
Logger::debug("Starting in DEBUG mode!");
}
else Logger::set(Config::getS("log_level"));
Logger::info("Logger set to " + (Global::debug ? "DEBUG" : Config::getS("log_level")));
for (const auto& err_str : load_warnings) Logger::warning(err_str);
}
init_config();
//? Try to find and set a UTF-8 locale
if (std::setlocale(LC_ALL, "") != nullptr and not s_contains((string)std::setlocale(LC_ALL, ""), ";")
@ -920,7 +954,7 @@ int main(int argc, char **argv) {
else {
string found;
bool set_failure{};
for (const auto loc_env : array{"LANG", "LC_ALL"}) {
for (const auto loc_env : array{"LANG", "LC_ALL", "LC_CTYPE"}) {
if (std::getenv(loc_env) != nullptr and str_to_upper(s_replace((string)std::getenv(loc_env), "-", "")).ends_with("UTF8")) {
found = std::getenv(loc_env);
if (std::setlocale(LC_ALL, found.c_str()) == nullptr) {
@ -1035,6 +1069,7 @@ int main(int argc, char **argv) {
std::signal(SIGCONT, _signal_handler);
std::signal(SIGWINCH, _signal_handler);
std::signal(SIGUSR1, _signal_handler);
std::signal(SIGUSR2, _signal_handler);
sigset_t mask;
sigemptyset(&mask);
@ -1086,9 +1121,27 @@ int main(int argc, char **argv) {
try {
while (not true not_eq not false) {
//? Check for exceptions in secondary thread and exit with fail signal if true
if (Global::thread_exception) clean_quit(1);
else if (Global::should_quit) clean_quit(0);
else if (Global::should_sleep) { Global::should_sleep = false; _sleep(); }
if (Global::thread_exception) {
clean_quit(1);
}
else if (Global::should_quit) {
clean_quit(0);
}
else if (Global::should_sleep) {
Global::should_sleep = false;
_sleep();
}
//? Hot reload config from CTRL + R or SIGUSR2
else if (Global::reload_conf) {
Global::reload_conf = false;
if (Runner::active) Runner::stop();
Config::unlock();
init_config();
Theme::updateThemes();
Theme::setTheme();
Draw::banner_gen(0, 0, false, true);
Global::resized = true;
}
//? Make sure terminal size hasn't changed (in case of SIGWINCH not working properly)
term_resize(Global::resized);
@ -1123,9 +1176,9 @@ int main(int argc, char **argv) {
update_ms = Config::getI("update_ms");
future_time = time_ms() + update_ms;
}
else if (future_time - current_time > update_ms)
else if (future_time - current_time > update_ms) {
future_time = current_time;
}
//? Poll for input and process any input detected
else if (Input::poll(min((uint64_t)1000, future_time - current_time))) {
if (not Runner::active) Config::unlock();

View file

@ -199,6 +199,8 @@ namespace Config {
{"selected_battery", "#* Which battery to use if multiple are present. \"Auto\" for auto detection."},
{"show_battery_watts", "#* Show power stats of battery next to charge indicator."},
{"log_level", "#* Set loglevel for \"~/.config/btop/btop.log\" levels are: \"ERROR\" \"WARNING\" \"INFO\" \"DEBUG\".\n"
"#* The level set includes all lower levels, i.e. \"DEBUG\" will show all logging info."},
#ifdef GPU_SUPPORT
@ -293,6 +295,7 @@ namespace Config {
{"net_auto", true},
{"net_sync", true},
{"show_battery", true},
{"show_battery_watts", true},
{"vim_keys", false},
{"tty_mode", false},
{"disk_free_priv", false},
@ -729,9 +732,9 @@ namespace Config {
if (geteuid() != Global::real_uid and seteuid(Global::real_uid) != 0) return;
std::ofstream cwrite(conf_file, std::ios::trunc);
if (cwrite.good()) {
cwrite << "#? Config file for btop v. " << Global::Version;
cwrite << "#? Config file for btop v. " << Global::Version << "\n";
for (auto [name, description] : descriptions) {
cwrite << "\n\n" << (description.empty() ? "" : description + "\n")
cwrite << "\n" << (description.empty() ? "" : description + "\n")
<< name << " = ";
if (strings.contains(name))
cwrite << "\"" << strings.at(name) << "\"";
@ -739,6 +742,7 @@ namespace Config {
cwrite << ints.at(name);
else if (bools.contains(name))
cwrite << (bools.at(name) ? "True" : "False");
cwrite << "\n";
}
}
}

View file

@ -706,6 +706,7 @@ namespace Cpu {
if (Config::getB("show_battery") and has_battery) {
static int old_percent{}; // defaults to = 0
static long old_seconds{}; // defaults to = 0
static float old_watts{}; // defaults to = 0
static string old_status;
static Draw::Meter bat_meter {10, "cpu", true};
static const std::unordered_map<string, string> bat_symbols = {
@ -715,16 +716,18 @@ namespace Cpu {
{"unknown", ""}
};
const auto& [percent, seconds, status] = current_bat;
const auto& [percent, watts, seconds, status] = current_bat;
if (redraw or percent != old_percent or seconds != old_seconds or status != old_status) {
if (redraw or percent != old_percent or (watts != old_watts and Config::getB("show_battery_watts")) or seconds != old_seconds or status != old_status) {
old_percent = percent;
old_watts = watts;
old_seconds = seconds;
old_status = status;
const string str_time = (seconds > 0 ? sec_to_dhms(seconds, true, true) : "");
const string str_time = (seconds > 0 ? sec_to_dhms(seconds, false, true) : "");
const string str_percent = to_string(percent) + '%';
const string str_watts = (watts != -1 and Config::getB("show_battery_watts") ? fmt::format("{:.2f}", watts) + 'W' : "");
const auto& bat_symbol = bat_symbols.at((bat_symbols.contains(status) ? status : "unknown"));
const int current_len = (Term::width >= 100 ? 11 : 0) + str_time.size() + str_percent.size() + to_string(Config::getI("update_ms")).size();
const int current_len = (Term::width >= 100 ? 11 : 0) + str_time.size() + str_percent.size() + str_watts.size() + to_string(Config::getI("update_ms")).size();
const int current_pos = Term::width - current_len - 17;
if ((bat_pos != current_pos or bat_len != current_len) and bat_pos > 0 and not redraw)
@ -734,7 +737,7 @@ namespace Cpu {
out += Mv::to(y, bat_pos) + title_left + Theme::c("title") + Fx::b + "BAT" + bat_symbol + ' ' + str_percent
+ (Term::width >= 100 ? Fx::ub + ' ' + bat_meter(percent) + Fx::b : "")
+ (not str_time.empty() ? ' ' + Theme::c("title") + str_time : " ") + Fx::ub + title_right;
+ (not str_time.empty() ? ' ' + Theme::c("title") + str_time : "") + (not str_watts.empty() ? " " + Theme::c("title") + Fx::b + str_watts : "") + Fx::ub + title_right;
}
}
else if (bat_pos > 0) {
@ -1361,6 +1364,7 @@ namespace Net {
int x = 1, y, width = 20, height;
int b_x, b_y, b_width, b_height, d_graph_height, u_graph_height;
bool shown = true, redraw = true;
const int MAX_IFNAMSIZ = 15;
string old_ip;
std::unordered_map<string, Draw::Graph> graphs;
string box;
@ -1381,7 +1385,7 @@ namespace Net {
out.reserve(width * height);
const string title_left = Theme::c("net_box") + Fx::ub + Symbols::title_left;
const string title_right = Theme::c("net_box") + Fx::ub + Symbols::title_right;
const int i_size = min((int)selected_iface.size(), 10);
const int i_size = min((int)selected_iface.size(), MAX_IFNAMSIZ);
const long long down_max = (net_auto ? safeVal(graph_max, "download"s) : ((long long)(Config::getI("net_download")) << 20) / 8);
const long long up_max = (net_auto ? safeVal(graph_max, "upload"s) : ((long long)(Config::getI("net_upload")) << 20) / 8);
@ -1403,7 +1407,7 @@ namespace Net {
//? Interface selector and buttons
out += Mv::to(y, x+width - i_size - 9) + title_left + Fx::b + Theme::c("hi_fg") + "<b " + Theme::c("title")
+ uresize(selected_iface, 10) + Theme::c("hi_fg") + " n>" + title_right
+ uresize(selected_iface, MAX_IFNAMSIZ) + Theme::c("hi_fg") + " n>" + title_right
+ Mv::to(y, x+width - i_size - 15) + title_left + Theme::c("hi_fg") + (safeVal(net.stat, "download"s).offset + safeVal(net.stat, "upload"s).offset > 0 ? Fx::b : "") + 'z'
+ Theme::c("title") + "ero" + title_right;
Input::mouse_mappings["b"] = {y, x+width - i_size - 8, 1, 3};
@ -2238,3 +2242,4 @@ namespace Draw {
}
}
}

View file

@ -41,6 +41,7 @@ namespace Input {
//* Map for translating key codes to readable values
const std::unordered_map<string, string> Key_escapes = {
{"\033", "escape"},
{"\x12", "ctrl_r"},
{"\n", "enter"},
{" ", "space"},
{"\x7f", "backspace"},
@ -258,8 +259,10 @@ namespace Input {
Draw::calcSizes();
Runner::run("all", false, true);
return;
}
else
} else if (is_in(key, "ctrl_r")) {
kill(getpid(), SIGUSR2);
return;
} else
keep_going = true;
if (not keep_going) return;

View file

@ -56,7 +56,7 @@ namespace Input {
//* Last entered key
extern deque<string> history;
//* Poll keyboard & mouse input for <timeout> ms and return input availabilty as a bool
//* Poll keyboard & mouse input for <timeout> ms and return input availability as a bool
bool poll(const uint64_t timeout=0);
//* Get a key or mouse action from input

View file

@ -177,6 +177,7 @@ namespace Menu {
{"F2, o", "Shows options."},
{"F1, ?, h", "Shows this window."},
{"ctrl + z", "Sleep program and put in background."},
{"ctrl + r", "Reloads config file from disk."},
{"q, ctrl + c", "Quits program."},
{"+, -", "Add/Subtract 100ms to/from update timer."},
{"Up, Down", "Select in process list."},
@ -190,7 +191,7 @@ namespace Menu {
{"z", "Toggle totals reset for current network device"},
{"a", "Toggle auto scaling for the network graphs."},
{"y", "Toggle synced scaling mode for network graphs."},
{"f, /", "To enter a process filter."},
{"f, /", "To enter a process filter. Start with ! for regex."},
{"delete", "Clear any entered filter."},
{"c", "Toggle per-core cpu usage of processes."},
{"r", "Reverse sorting order in processes box."},
@ -353,6 +354,11 @@ namespace Menu {
"Can be both batteries and UPS.",
"",
"\"Auto\" for auto detection."},
{"show_battery_watts",
"Show battery power.",
"",
"Show discharge power when discharging.",
"Show charging power when charging."},
{"log_level",
"Set loglevel for error.log",
"",
@ -484,7 +490,7 @@ namespace Menu {
"Kelvin, 0 = absolute zero, 1 degree change",
"equals 1 degree change in Celsius.",
"",
"Rankine, 0 = abosulte zero, 1 degree change",
"Rankine, 0 = absolute zero, 1 degree change",
"equals 1 degree change in Fahrenheit."},
{"show_cpu_freq",
"Show CPU frequency.",
@ -645,7 +651,7 @@ namespace Menu {
"",
"Begin line with \"exclude=\" to change to",
"exclude filter.",
"Oterwise defaults to \"most include\" filter.",
"Otherwise defaults to \"most include\" filter.",
"",
"Example:",
"\"exclude=/boot /home/user\""},

View file

@ -17,6 +17,8 @@ tab-size = 4
*/
#include <ranges>
#include <regex>
#include <string>
#include "btop_config.hpp"
#include "btop_shared.hpp"
@ -111,6 +113,22 @@ namespace Proc {
}
}
bool matches_filter(const proc_info& proc, const std::string& filter) {
if (filter.starts_with("!")) {
if (filter.size() == 1) {
return true;
}
std::regex regex{filter.substr(1), std::regex::extended};
return std::regex_search(std::to_string(proc.pid), regex) ||
std::regex_search(proc.name, regex) || std::regex_match(proc.cmd, regex) ||
std::regex_search(proc.user, regex);
} else {
return s_contains(std::to_string(proc.pid), filter) ||
s_contains_ic(proc.name, filter) || s_contains_ic(proc.cmd, filter) ||
s_contains_ic(proc.user, filter);
}
}
void _tree_gen(proc_info& cur_proc, vector<proc_info>& in_procs, vector<tree_proc>& out_procs,
int cur_depth, bool collapsed, const string& filter, bool found, bool no_update, bool should_filter) {
auto cur_pos = out_procs.size();
@ -118,10 +136,7 @@ namespace Proc {
//? If filtering, include children of matching processes
if (not found and (should_filter or not filter.empty())) {
if (not s_contains(std::to_string(cur_proc.pid), filter)
and not s_contains_ic(cur_proc.name, filter)
and not s_contains_ic(cur_proc.cmd, filter)
and not s_contains_ic(cur_proc.user, filter)) {
if (!matches_filter(cur_proc, filter)) {
filtering = true;
cur_proc.filtered = true;
filter_found++;

View file

@ -25,10 +25,19 @@ tab-size = 4
#include <string>
#include <tuple>
#include <vector>
#include <ifaddrs.h>
#include <unordered_map>
#include <unistd.h>
// From `man 3 getifaddrs`: <net/if.h> must be included before <ifaddrs.h>
// clang-format off
#include <net/if.h>
#include <ifaddrs.h>
// clang-format on
#if defined(__FreeBSD__) || defined(__OpenBSD__)
# include <kvm.h>
#endif
using std::array;
using std::atomic;
using std::deque;
@ -83,6 +92,15 @@ namespace Shared {
void init();
extern long coreCount, page_size, clk_tck;
#if defined(__FreeBSD__) || defined(__OpenBSD__)
struct KvmDeleter {
void operator()(kvm_t* handle) {
kvm_close(handle);
}
};
using KvmPtr = std::unique_ptr<kvm_t, KvmDeleter>;
#endif
}
@ -178,7 +196,7 @@ namespace Cpu {
extern string cpuName, cpuHz;
extern vector<string> available_fields;
extern vector<string> available_sensors;
extern tuple<int, long, string> current_bat;
extern tuple<int, float, long, string> current_bat;
struct cpu_info {
std::unordered_map<string, deque<long long>> cpu_percent = {
@ -213,7 +231,7 @@ namespace Cpu {
auto get_cpuHz() -> string;
//* Get battery info from /sys
auto get_battery() -> tuple<int, long, string>;
auto get_battery() -> tuple<int, float, long, string>;
}
namespace Mem {
@ -289,6 +307,17 @@ namespace Net {
bool connected{};
};
class IfAddrsPtr {
struct ifaddrs* ifaddr;
int status;
public:
IfAddrsPtr() { status = getifaddrs(&ifaddr); }
~IfAddrsPtr() { freeifaddrs(ifaddr); }
[[nodiscard]] constexpr auto operator()() -> struct ifaddrs* { return ifaddr; }
[[nodiscard]] constexpr auto get() -> struct ifaddrs* { return ifaddr; }
[[nodiscard]] constexpr auto get_status() const noexcept -> int { return status; };
};
extern std::unordered_map<string, net_info> current_net;
//* Collect net upload/download stats
@ -395,6 +424,8 @@ namespace Proc {
void tree_sort(vector<tree_proc>& proc_vec, const string& sorting,
bool reverse, int& c_index, const int index_max, bool collapsed = false);
bool matches_filter(const proc_info& proc, const std::string& filter);
//* Generate process tree list
void _tree_gen(proc_info& cur_proc, vector<proc_info>& in_procs, vector<tree_proc>& out_procs,
int cur_depth, bool collapsed, const string& filter,

View file

@ -381,11 +381,16 @@ namespace Theme {
if (themefile.good()) {
Logger::debug("Loading theme file: " + filename);
while (not themefile.bad()) {
if (themefile.peek() == '#') {
themefile.ignore(SSmax, '\n');
continue;
}
themefile.ignore(SSmax, '[');
if (themefile.eof()) break;
string name, value;
getline(themefile, name, ']');
if (not Default_theme.contains(name)) {
themefile.ignore(SSmax, '\n');
continue;
}
themefile.ignore(SSmax, '=');
@ -394,6 +399,7 @@ namespace Theme {
if (themefile.peek() == '"') {
themefile.ignore(1);
getline(themefile, value, '"');
themefile.ignore(SSmax, '\n');
}
else getline(themefile, value, '\n');

View file

@ -32,7 +32,7 @@ namespace Theme {
extern std::filesystem::path theme_dir;
extern std::filesystem::path user_theme_dir;
//* Contains "Default" and "TTY" at indeces 0 and 1, otherwise full paths to theme files
//* Contains "Default" and "TTY" at indices 0 and 1, otherwise full paths to theme files
extern vector<string> themes;
//* Generate escape sequence for 24-bit or 256 color and return as a string

View file

@ -89,7 +89,7 @@ namespace Term {
}
bool refresh(bool only_check) {
// Query dimensions of '/dev/tty' of the 'STDOUT_FILENO' isn't avaiable.
// Query dimensions of '/dev/tty' of the 'STDOUT_FILENO' isn't available.
// This variable is set in those cases to avoid calls to ioctl
constinit static bool uses_dev_tty = false;
struct winsize wsize {};
@ -644,7 +644,7 @@ namespace Logger {
size_t loglevel;
fs::path logfile;
//* Wrapper for lowering priviliges if using SUID bit and currently isn't using real userid
//* Wrapper for lowering privileges if using SUID bit and currently isn't using real userid
class lose_priv {
int status = -1;
public:

View file

@ -18,6 +18,10 @@ tab-size = 4
#pragma once
#if !defined(NDEBUG)
# define BTOP_DEBUG
#endif
#include <algorithm> // for std::ranges::count_if
#include <array>
#include <atomic>
@ -42,11 +46,9 @@ tab-size = 4
#define HOST_NAME_MAX 64
#endif
#endif
#define FMT_HEADER_ONLY
#include "fmt/core.h"
#include "fmt/format.h"
#include "fmt/ostream.h"
#include "fmt/ranges.h"
using std::array;
using std::atomic;
@ -112,7 +114,7 @@ namespace Mv {
//* Save cursor position
const string save = Fx::e + "s";
//* Restore saved cursor postion
//* Restore saved cursor position
const string restore = Fx::e + "u";
}
@ -284,7 +286,7 @@ namespace Tools {
return is_in(str, "true", "True");
}
//* Check if a string is a valid integer value (only postive)
//* Check if a string is a valid integer value (only positive)
inline bool isint(const string& str) {
return all_of(str.begin(), str.end(), ::isdigit);
}

10
src/config.h.in Normal file
View file

@ -0,0 +1,10 @@
// SPDX-License-Identifier: Apache-2.0
#pragma once
#include <string_view>
constexpr std::string_view GIT_COMMIT = "@GIT_COMMIT@";
constexpr std::string_view COMPILER = "@COMPILER@";
constexpr std::string_view COMPILER_VERSION = "@COMPILER_VERSION@";
constexpr std::string_view CONFIGURE_COMMAND = "@CONFIGURE_COMMAND@";

View file

@ -189,25 +189,13 @@ namespace Shared {
Logger::debug("Init -> Mem::get_zpools()");
Mem::get_zpools();
}
//* RAII wrapper for kvm_openfiles
class kvm_openfiles_wrapper {
kvm_t* kd = nullptr;
public:
kvm_openfiles_wrapper(const char* execf, const char* coref, const char* swapf, int flags, char* err) {
this->kd = kvm_openfiles(execf, coref, swapf, flags, err);
}
~kvm_openfiles_wrapper() { kvm_close(kd); }
auto operator()() -> kvm_t* { return kd; }
};
} // namespace Shared
namespace Cpu {
string cpuName;
string cpuHz;
bool has_battery = true;
tuple<int, long, string> current_bat;
tuple<int, float, long, string> current_bat;
const array<string, 10> time_names = {"user", "nice", "system", "idle"};
@ -277,7 +265,7 @@ namespace Cpu {
got_sensors = true;
int temp;
size_t size = sizeof(temp);
sysctlbyname("dev.cpu.0.coretemp.tjmax", &temp, &size, nullptr, 0); //asuming the max temp is same for all cores
sysctlbyname("dev.cpu.0.coretemp.tjmax", &temp, &size, nullptr, 0); //assuming the max temp is same for all cores
temp = (temp - 2732) / 10; // since it's an int, it's multiplied by 10, and offset to absolute zero...
current_cpu.temp_max = temp;
}
@ -373,10 +361,11 @@ namespace Cpu {
return core_map;
}
auto get_battery() -> tuple<int, long, string> {
if (not has_battery) return {0, 0, ""};
auto get_battery() -> tuple<int, float, long, string> {
if (not has_battery) return {0, 0, 0, ""};
long seconds = -1;
float watts = -1;
uint32_t percent = -1;
size_t size = sizeof(percent);
string status = "discharging";
@ -388,6 +377,10 @@ namespace Cpu {
if (sysctlbyname("hw.acpi.battery.time", &seconds, &size, nullptr, 0) < 0) {
seconds = 0;
}
size = sizeof(watts);
if (sysctlbyname("hw.acpi.battery.rate", &watts, &size, nullptr, 0) < 0) {
watts = -1;
}
int state;
size = sizeof(state);
if (sysctlbyname("hw.acpi.battery.state", &state, &size, nullptr, 0) < 0) {
@ -402,7 +395,7 @@ namespace Cpu {
}
}
return {percent, seconds, status};
return {percent, watts, seconds, status};
}
auto collect(bool no_update) -> cpu_info & {
@ -668,9 +661,9 @@ namespace Mem {
if (show_swap) {
char buf[_POSIX2_LINE_MAX];
Shared::kvm_openfiles_wrapper kd(nullptr, _PATH_DEVNULL, nullptr, O_RDONLY, buf);
Shared::KvmPtr kd {kvm_openfiles(nullptr, _PATH_DEVNULL, nullptr, O_RDONLY, buf)};
struct kvm_swap swap[16];
int nswap = kvm_getswapinfo(kd(), swap, 16, 0);
int nswap = kvm_getswapinfo(kd.get(), swap, 16, 0);
int totalSwap = 0, usedSwap = 0;
for (int i = 0; i < nswap; i++) {
totalSwap += swap[i].ksw_total;
@ -823,17 +816,6 @@ namespace Net {
bool rescale = true;
uint64_t timestamp = 0;
//* RAII wrapper for getifaddrs
class getifaddr_wrapper {
struct ifaddrs *ifaddr;
public:
int status;
getifaddr_wrapper() { status = getifaddrs(&ifaddr); }
~getifaddr_wrapper() { freeifaddrs(ifaddr); }
auto operator()() -> struct ifaddrs * { return ifaddr; }
};
auto collect(bool no_update) -> net_info & {
auto &net = current_net;
auto &config_iface = Config::getS("net_iface");
@ -843,10 +825,10 @@ namespace Net {
if (not no_update and errors < 3) {
//? Get interface list using getifaddrs() wrapper
getifaddr_wrapper if_wrap{};
if (if_wrap.status != 0) {
IfAddrsPtr if_addrs {};
if (if_addrs.get_status() != 0) {
errors++;
Logger::error("Net::collect() -> getifaddrs() failed with id " + to_string(if_wrap.status));
Logger::error("Net::collect() -> getifaddrs() failed with id " + to_string(if_addrs.get_status()));
redraw = true;
return empty_net;
}
@ -858,7 +840,7 @@ namespace Net {
string ipv4, ipv6;
//? Iteration over all items in getifaddrs() list
for (auto *ifa = if_wrap(); ifa != nullptr; ifa = ifa->ifa_next) {
for (auto *ifa = if_addrs.get(); ifa != nullptr; ifa = ifa->ifa_next) {
if (ifa->ifa_addr == nullptr) continue;
family = ifa->ifa_addr->sa_family;
const auto &iface = ifa->ifa_name;
@ -925,7 +907,7 @@ namespace Net {
}
}
//? Get total recieved and transmitted bytes + device address if no ip was found
//? Get total received and transmitted bytes + device address if no ip was found
for (const auto &iface : interfaces) {
for (const string dir : {"download", "upload"}) {
auto &saved_stat = net.at(iface).stat.at(dir);
@ -1164,8 +1146,8 @@ namespace Proc {
int count = 0;
char buf[_POSIX2_LINE_MAX];
Shared::kvm_openfiles_wrapper kd(nullptr, _PATH_DEVNULL, nullptr, O_RDONLY, buf);
const struct kinfo_proc* kprocs = kvm_getprocs(kd(), KERN_PROC_PROC, 0, &count);
Shared::KvmPtr kd {kvm_openfiles(nullptr, _PATH_DEVNULL, nullptr, O_RDONLY, buf)};
const struct kinfo_proc* kprocs = kvm_getprocs(kd.get(), KERN_PROC_PROC, 0, &count);
for (int i = 0; i < count; i++) {
const struct kinfo_proc* kproc = &kprocs[i];
@ -1192,7 +1174,7 @@ namespace Proc {
continue;
}
new_proc.name = kproc->ki_comm;
char** argv = kvm_getargv(kd(), kproc, 0);
char** argv = kvm_getargv(kd.get(), kproc, 0);
if (argv) {
for (int i = 0; argv[i] and cmp_less(new_proc.cmd.size(), 1000); i++) {
new_proc.cmd += argv[i] + " "s;
@ -1257,18 +1239,13 @@ namespace Proc {
filter_found = 0;
for (auto& p : current_procs) {
if (not tree and not filter.empty()) {
if (not s_contains_ic(to_string(p.pid), filter)
and not s_contains_ic(p.name, filter)
and not s_contains_ic(p.cmd, filter)
and not s_contains_ic(p.user, filter)) {
p.filtered = true;
filter_found++;
}
else {
p.filtered = false;
}
if (!matches_filter(p, filter)) {
p.filtered = true;
filter_found++;
} else {
p.filtered = false;
}
else {
} else {
p.filtered = false;
}
}

View file

@ -158,39 +158,49 @@ namespace Gpu {
//? AMD data collection
namespace Rsmi {
//? RSMI defines, structs & typedefs
#define RSMI_DEVICE_NAME_BUFFER_SIZE 128
#if !defined(RSMI_STATIC)
//? RSMI defines, structs & typedefs
#define RSMI_MAX_NUM_FREQUENCIES 32
#define RSMI_STATUS_SUCCESS 0
#define RSMI_MEM_TYPE_VRAM 0
#define RSMI_TEMP_CURRENT 0
#define RSMI_TEMP_TYPE_EDGE 0
#define RSMI_CLK_TYPE_MEM 4
#define RSMI_CLK_TYPE_SYS 0
#define RSMI_TEMP_MAX 1
#define RSMI_MAX_NUM_FREQUENCIES_V5 32
#define RSMI_MAX_NUM_FREQUENCIES_V6 33
#define RSMI_STATUS_SUCCESS 0
#define RSMI_MEM_TYPE_VRAM 0
#define RSMI_TEMP_CURRENT 0
#define RSMI_TEMP_TYPE_EDGE 0
#define RSMI_CLK_TYPE_MEM 4
#define RSMI_CLK_TYPE_SYS 0
#define RSMI_TEMP_MAX 1
typedef int rsmi_status_t,
rsmi_temperature_metric_t,
rsmi_clk_type_t,
rsmi_memory_type_t;
struct rsmi_frequencies_t {uint32_t num_supported, current, frequency[RSMI_MAX_NUM_FREQUENCIES];};
struct rsmi_version_t {uint32_t major, minor, patch; const char* build;};
struct rsmi_frequencies_t_v5 {uint32_t num_supported, current; uint64_t frequency[RSMI_MAX_NUM_FREQUENCIES_V5];};
struct rsmi_frequencies_t_v6 {bool has_deep_sleep; uint32_t num_supported, current; uint64_t frequency[RSMI_MAX_NUM_FREQUENCIES_V6];};
//? Function pointers
rsmi_status_t (*rsmi_init)(uint64_t);
rsmi_status_t (*rsmi_shut_down)();
rsmi_status_t (*rsmi_version_get)(rsmi_version_t*);
rsmi_status_t (*rsmi_num_monitor_devices)(uint32_t*);
rsmi_status_t (*rsmi_dev_name_get)(uint32_t, char*, size_t);
rsmi_status_t (*rsmi_dev_power_cap_get)(uint32_t, uint32_t, uint64_t*);
rsmi_status_t (*rsmi_dev_temp_metric_get)(uint32_t, uint32_t, rsmi_temperature_metric_t, int64_t*);
rsmi_status_t (*rsmi_dev_busy_percent_get)(uint32_t, uint32_t*);
rsmi_status_t (*rsmi_dev_memory_busy_percent_get)(uint32_t, uint32_t*);
rsmi_status_t (*rsmi_dev_gpu_clk_freq_get)(uint32_t, rsmi_clk_type_t, rsmi_frequencies_t*);
rsmi_status_t (*rsmi_dev_gpu_clk_freq_get_v5)(uint32_t, rsmi_clk_type_t, rsmi_frequencies_t_v5*);
rsmi_status_t (*rsmi_dev_gpu_clk_freq_get_v6)(uint32_t, rsmi_clk_type_t, rsmi_frequencies_t_v6*);
rsmi_status_t (*rsmi_dev_power_ave_get)(uint32_t, uint32_t, uint64_t*);
rsmi_status_t (*rsmi_dev_memory_total_get)(uint32_t, rsmi_memory_type_t, uint64_t*);
rsmi_status_t (*rsmi_dev_memory_usage_get)(uint32_t, rsmi_memory_type_t, uint64_t*);
rsmi_status_t (*rsmi_dev_pci_throughput_get)(uint32_t, uint64_t*, uint64_t*, uint64_t*);
uint32_t version_major = 0;
//? Data
void* rsmi_dl_handle;
#endif
@ -294,7 +304,7 @@ namespace Cpu {
string cpuName;
string cpuHz;
bool has_battery = true;
tuple<int, long, string> current_bat;
tuple<int, float, long, string> current_bat;
const array time_names {
"user"s, "nice"s, "system"s, "idle"s, "iowait"s,
@ -438,7 +448,7 @@ namespace Cpu {
const int file_id = atoi(file.path().filename().c_str() + 4); // skip "temp" prefix
string file_path = file.path();
if (!s_contains(file_path, file_suffix)) {
if (!s_contains(file_path, file_suffix) or s_contains(file_path, "nvme")) {
continue;
}
@ -583,7 +593,7 @@ namespace Cpu {
cpuhz += " GHz";
}
else if (hz > 0)
cpuhz = to_string((int)round(hz)) + " MHz";
cpuhz = to_string((int)hz) + " MHz";
}
catch (const std::exception& e) {
@ -664,13 +674,14 @@ namespace Cpu {
}
struct battery {
fs::path base_dir, energy_now, energy_full, power_now, status, online;
fs::path base_dir, energy_now, charge_now, energy_full, charge_full, power_now, current_now, voltage_now, status, online;
string device_type;
bool use_energy = true;
bool use_energy_or_charge = true;
bool use_power = true;
};
auto get_battery() -> tuple<int, long, string> {
if (not has_battery) return {0, 0, ""};
auto get_battery() -> tuple<int, float, long, string> {
if (not has_battery) return {0, 0, 0, ""};
static string auto_sel;
static std::unordered_map<string, battery> batteries;
@ -702,19 +713,27 @@ namespace Cpu {
}
if (fs::exists(bat_dir / "energy_now")) new_bat.energy_now = bat_dir / "energy_now";
else if (fs::exists(bat_dir / "charge_now")) new_bat.energy_now = bat_dir / "charge_now";
else new_bat.use_energy = false;
else if (fs::exists(bat_dir / "charge_now")) new_bat.charge_now = bat_dir / "charge_now";
else new_bat.use_energy_or_charge = false;
if (fs::exists(bat_dir / "energy_full")) new_bat.energy_full = bat_dir / "energy_full";
else if (fs::exists(bat_dir / "charge_full")) new_bat.energy_full = bat_dir / "charge_full";
else new_bat.use_energy = false;
else if (fs::exists(bat_dir / "charge_full")) new_bat.charge_full = bat_dir / "charge_full";
else new_bat.use_energy_or_charge = false;
if (not new_bat.use_energy and not fs::exists(bat_dir / "capacity")) {
if (not new_bat.use_energy_or_charge and not fs::exists(bat_dir / "capacity")) {
continue;
}
if (fs::exists(bat_dir / "power_now")) new_bat.power_now = bat_dir / "power_now";
else if (fs::exists(bat_dir / "current_now")) new_bat.power_now = bat_dir / "current_now";
if (fs::exists(bat_dir / "power_now")) {
new_bat.power_now = bat_dir / "power_now";
}
else if ((fs::exists(bat_dir / "current_now")) and (fs::exists(bat_dir / "voltage_now"))) {
new_bat.current_now = bat_dir / "current_now";
new_bat.voltage_now = bat_dir / "voltage_now";
}
else {
new_bat.use_power = false;
}
if (fs::exists(bat_dir / "AC0/online")) new_bat.online = bat_dir / "AC0/online";
else if (fs::exists(bat_dir / "AC/online")) new_bat.online = bat_dir / "AC/online";
@ -729,7 +748,7 @@ namespace Cpu {
}
if (batteries.empty()) {
has_battery = false;
return {0, 0, ""};
return {0, 0, 0, ""};
}
}
@ -749,15 +768,9 @@ namespace Cpu {
int percent = -1;
long seconds = -1;
float watts = -1;
//? Try to get battery percentage
if (b.use_energy) {
try {
percent = round(100.0 * stoll(readfile(b.energy_now, "-1")) / stoll(readfile(b.energy_full, "1")));
}
catch (const std::invalid_argument&) { }
catch (const std::out_of_range&) { }
}
if (percent < 0) {
try {
percent = stoll(readfile(b.base_dir / "capacity", "-1"));
@ -765,9 +778,23 @@ namespace Cpu {
catch (const std::invalid_argument&) { }
catch (const std::out_of_range&) { }
}
if (b.use_energy_or_charge and percent < 0) {
try {
percent = round(100.0 * stoll(readfile(b.energy_now, "-1")) / stoll(readfile(b.energy_full, "1")));
}
catch (const std::invalid_argument&) { }
catch (const std::out_of_range&) { }
}
if (b.use_energy_or_charge and percent < 0) {
try {
percent = round(100.0 * stoll(readfile(b.charge_now, "-1")) / stoll(readfile(b.charge_full, "1")));
}
catch (const std::invalid_argument&) { }
catch (const std::out_of_range&) { }
}
if (percent < 0) {
has_battery = false;
return {0, 0, ""};
return {0, 0, 0, ""};
}
//? Get charging/discharging status
@ -781,13 +808,23 @@ namespace Cpu {
//? Get seconds to empty
if (not is_in(status, "charging", "full")) {
if (b.use_energy and not b.power_now.empty()) {
try {
seconds = round((double)stoll(readfile(b.energy_now, "0")) / stoll(readfile(b.power_now, "1")) * 3600);
if (b.use_energy_or_charge ) {
if (not b.power_now.empty()) {
try {
seconds = round((double)stoll(readfile(b.energy_now, "0")) / stoll(readfile(b.power_now, "1")) * 3600);
}
catch (const std::invalid_argument&) { }
catch (const std::out_of_range&) { }
}
else if (not b.current_now.empty()) {
try {
seconds = round((double)stoll(readfile(b.charge_now, "0")) / (double)stoll(readfile(b.current_now, "1")) * 3600);
}
catch (const std::invalid_argument&) { }
catch (const std::out_of_range&) { }
}
catch (const std::invalid_argument&) { }
catch (const std::out_of_range&) { }
}
if (seconds < 0 and fs::exists(b.base_dir / "time_to_empty")) {
try {
seconds = stoll(readfile(b.base_dir / "time_to_empty", "0")) * 60;
@ -797,7 +834,26 @@ namespace Cpu {
}
}
return {percent, seconds, status};
//? Get power draw
if (b.use_power) {
if (not b.power_now.empty()) {
try {
watts = (float)stoll(readfile(b.power_now, "-1")) / 1000000.0;
}
catch (const std::invalid_argument&) { }
catch (const std::out_of_range&) { }
}
else if (not b.voltage_now.empty() and not b.current_now.empty()) {
try {
watts = (float)stoll(readfile(b.current_now, "-1")) / 1000000.0 * stoll(readfile(b.voltage_now, "1")) / 1000000.0;
}
catch (const std::invalid_argument&) { }
catch (const std::out_of_range&) { }
}
}
return {percent, watts, seconds, status};
}
auto collect(bool no_update) -> cpu_info& {
@ -1232,6 +1288,7 @@ namespace Gpu {
"librocm_smi64.so",
"librocm_smi64.so.5", // fedora
"librocm_smi64.so.1.0", // debian
"librocm_smi64.so.6"
};
for (const auto& l : libRocAlts) {
@ -1259,13 +1316,13 @@ namespace Gpu {
LOAD_SYM(rsmi_init);
LOAD_SYM(rsmi_shut_down);
LOAD_SYM(rsmi_version_get);
LOAD_SYM(rsmi_num_monitor_devices);
LOAD_SYM(rsmi_dev_name_get);
LOAD_SYM(rsmi_dev_power_cap_get);
LOAD_SYM(rsmi_dev_temp_metric_get);
LOAD_SYM(rsmi_dev_busy_percent_get);
LOAD_SYM(rsmi_dev_memory_busy_percent_get);
LOAD_SYM(rsmi_dev_gpu_clk_freq_get);
LOAD_SYM(rsmi_dev_power_ave_get);
LOAD_SYM(rsmi_dev_memory_total_get);
LOAD_SYM(rsmi_dev_memory_usage_get);
@ -1281,6 +1338,27 @@ namespace Gpu {
return false;
}
#if !defined(RSMI_STATIC)
//? Check version
rsmi_version_t version;
result = rsmi_version_get(&version);
if (result != RSMI_STATUS_SUCCESS) {
Logger::warning("ROCm SMI: Failed to get version");
return false;
} else if (version.major == 5) {
if ((rsmi_dev_gpu_clk_freq_get_v5 = (decltype(rsmi_dev_gpu_clk_freq_get_v5))load_rsmi_sym("rsmi_dev_gpu_clk_freq_get")) == nullptr)
return false;
// In the release tarballs of rocm 6.0.0 and 6.0.2 the version queried with rsmi_version_get is 7.0.0.0
} else if (version.major == 6 || version.major == 7) {
if ((rsmi_dev_gpu_clk_freq_get_v6 = (decltype(rsmi_dev_gpu_clk_freq_get_v6))load_rsmi_sym("rsmi_dev_gpu_clk_freq_get")) == nullptr)
return false;
} else {
Logger::warning("ROCm SMI: Dynamic loading only supported for version 5 and 6");
return false;
}
version_major = version.major;
#endif
//? Device count
result = rsmi_num_monitor_devices(&device_count);
if (result != RSMI_STATUS_SUCCESS) {
@ -1321,8 +1399,8 @@ namespace Gpu {
for (uint32_t i = 0; i < device_count; ++i) {
if constexpr(is_init) {
//? Device name
char name[NVML_DEVICE_NAME_BUFFER_SIZE]; // ROCm SMI does not provide a constant for this as far as I can tell, this should be good enough
result = rsmi_dev_name_get(i, name, NVML_DEVICE_NAME_BUFFER_SIZE);
char name[RSMI_DEVICE_NAME_BUFFER_SIZE];
result = rsmi_dev_name_get(i, name, RSMI_DEVICE_NAME_BUFFER_SIZE);
if (result != RSMI_STATUS_SUCCESS)
Logger::warning("ROCm SMI: Failed to get device name");
else gpu_names[Nvml::device_count + i] = string(name);
@ -1364,7 +1442,46 @@ namespace Gpu {
if constexpr(is_init) gpus_slice[i].supported_functions.mem_utilization = false;
} else gpus_slice[i].mem_utilization_percent.push_back((long long)utilization);
}
#if !defined(RSMI_STATIC)
//? Clock speeds
if (gpus_slice[i].supported_functions.gpu_clock) {
if (version_major == 5) {
rsmi_frequencies_t_v5 frequencies;
result = rsmi_dev_gpu_clk_freq_get_v5(i, RSMI_CLK_TYPE_SYS, &frequencies);
if (result != RSMI_STATUS_SUCCESS) {
Logger::warning("ROCm SMI: Failed to get GPU clock speed: ");
if constexpr(is_init) gpus_slice[i].supported_functions.gpu_clock = false;
} else gpus_slice[i].gpu_clock_speed = (long long)frequencies.frequency[frequencies.current]/1000000; // Hz to MHz
}
else if (version_major == 6 || version_major == 7) {
rsmi_frequencies_t_v6 frequencies;
result = rsmi_dev_gpu_clk_freq_get_v6(i, RSMI_CLK_TYPE_SYS, &frequencies);
if (result != RSMI_STATUS_SUCCESS) {
Logger::warning("ROCm SMI: Failed to get GPU clock speed: ");
if constexpr(is_init) gpus_slice[i].supported_functions.gpu_clock = false;
} else gpus_slice[i].gpu_clock_speed = (long long)frequencies.frequency[frequencies.current]/1000000; // Hz to MHz
}
}
if (gpus_slice[i].supported_functions.mem_clock) {
if (version_major == 5) {
rsmi_frequencies_t_v5 frequencies;
result = rsmi_dev_gpu_clk_freq_get_v5(i, RSMI_CLK_TYPE_MEM, &frequencies);
if (result != RSMI_STATUS_SUCCESS) {
Logger::warning("ROCm SMI: Failed to get VRAM clock speed: ");
if constexpr(is_init) gpus_slice[i].supported_functions.mem_clock = false;
} else gpus_slice[i].mem_clock_speed = (long long)frequencies.frequency[frequencies.current]/1000000; // Hz to MHz
}
else if (version_major == 6 || version_major == 7) {
rsmi_frequencies_t_v6 frequencies;
result = rsmi_dev_gpu_clk_freq_get_v6(i, RSMI_CLK_TYPE_MEM, &frequencies);
if (result != RSMI_STATUS_SUCCESS) {
Logger::warning("ROCm SMI: Failed to get VRAM clock speed: ");
if constexpr(is_init) gpus_slice[i].supported_functions.mem_clock = false;
} else gpus_slice[i].mem_clock_speed = (long long)frequencies.frequency[frequencies.current]/1000000; // Hz to MHz
}
}
#else
//? Clock speeds
if (gpus_slice[i].supported_functions.gpu_clock) {
rsmi_frequencies_t frequencies;
@ -1383,6 +1500,7 @@ namespace Gpu {
if constexpr(is_init) gpus_slice[i].supported_functions.mem_clock = false;
} else gpus_slice[i].mem_clock_speed = (long long)frequencies.frequency[frequencies.current]/1000000; // Hz to MHz
}
#endif
//? Power usage & state
if (gpus_slice[i].supported_functions.pwr_usage) {
@ -1391,7 +1509,10 @@ namespace Gpu {
if (result != RSMI_STATUS_SUCCESS) {
Logger::warning("ROCm SMI: Failed to get GPU power usage");
if constexpr(is_init) gpus_slice[i].supported_functions.pwr_usage = false;
} else gpus_slice[i].gpu_percent.at("gpu-pwr-totals").push_back(clamp((long long)round((double)gpus_slice[i].pwr_usage * 100.0 / (double)gpus_slice[i].pwr_max_usage), 0ll, 100ll));
} else {
gpus_slice[i].pwr_usage = (long long)power / 1000;
gpus_slice[i].gpu_percent.at("gpu-pwr-totals").push_back(clamp((long long)round((double)gpus_slice[i].pwr_usage * 100.0 / (double)gpus_slice[i].pwr_max_usage), 0ll, 100ll));
}
if constexpr(is_init) gpus_slice[i].supported_functions.pwr_state = false;
}
@ -1946,7 +2067,7 @@ namespace Mem {
if (access(zfs_pool_stat_path.c_str(), R_OK) == 0) {
return zfs_pool_stat_path;
} else {
Logger::debug("Cant access folder: " + zfs_pool_stat_path.string());
Logger::debug("Can't access folder: " + zfs_pool_stat_path.string());
return "";
}
}
@ -2084,16 +2205,6 @@ namespace Net {
bool rescale{true};
uint64_t timestamp{};
//* RAII wrapper for getifaddrs
class getifaddr_wrapper {
struct ifaddrs* ifaddr;
public:
int status;
getifaddr_wrapper() { status = getifaddrs(&ifaddr); }
~getifaddr_wrapper() { freeifaddrs(ifaddr); }
auto operator()() -> struct ifaddrs* { return ifaddr; }
};
auto collect(bool no_update) -> net_info& {
if (Runner::stopping) return empty_net;
auto& net = current_net;
@ -2104,10 +2215,10 @@ namespace Net {
if (not no_update and errors < 3) {
//? Get interface list using getifaddrs() wrapper
getifaddr_wrapper if_wrap {};
if (if_wrap.status != 0) {
IfAddrsPtr if_addrs {};
if (if_addrs.get_status() != 0) {
errors++;
Logger::error("Net::collect() -> getifaddrs() failed with id " + to_string(if_wrap.status));
Logger::error("Net::collect() -> getifaddrs() failed with id " + to_string(if_addrs.get_status()));
redraw = true;
return empty_net;
}
@ -2119,7 +2230,7 @@ namespace Net {
string ipv4, ipv6;
//? Iteration over all items in getifaddrs() list
for (auto* ifa = if_wrap(); ifa != nullptr; ifa = ifa->ifa_next) {
for (auto* ifa = if_addrs.get(); ifa != nullptr; ifa = ifa->ifa_next) {
if (ifa->ifa_addr == nullptr) continue;
family = ifa->ifa_addr->sa_family;
const auto& iface = ifa->ifa_name;
@ -2161,7 +2272,7 @@ namespace Net {
} //else, ignoring family==AF_PACKET (see man 3 getifaddrs) which is the first one in the `for` loop.
}
//? Get total recieved and transmitted bytes + device address if no ip was found
//? Get total received and transmitted bytes + device address if no ip was found
for (const auto& iface : interfaces) {
if (net.at(iface).ipv4.empty() and net.at(iface).ipv6.empty())
net.at(iface).ipv4 = readfile("/sys/class/net/" + iface + "/address");
@ -2688,18 +2799,13 @@ namespace Proc {
filter_found = 0;
for (auto& p : current_procs) {
if (not tree and not filter.empty()) {
if (not s_contains_ic(to_string(p.pid), filter)
and not s_contains_ic(p.name, filter)
and not s_contains_ic(p.cmd, filter)
and not s_contains_ic(p.user, filter)) {
p.filtered = true;
filter_found++;
}
else {
p.filtered = false;
}
if (!matches_filter(p, filter)) {
p.filtered = true;
filter_found++;
} else {
p.filtered = false;
}
else {
} else {
p.filtered = false;
}
}

View file

@ -184,25 +184,13 @@ namespace Shared {
Mem::old_uptime = system_uptime();
Mem::collect();
}
//* RAII wrapper for kvm_openfiles
class kvm_openfiles_wrapper {
kvm_t* kd = nullptr;
public:
kvm_openfiles_wrapper(const char* execf, const char* coref, const char* swapf, int flags, char* err) {
this->kd = kvm_openfiles(execf, coref, swapf, flags, err);
}
~kvm_openfiles_wrapper() { kvm_close(kd); }
auto operator()() -> kvm_t* { return kd; }
};
} // namespace Shared
namespace Cpu {
string cpuName;
string cpuHz;
bool has_battery = true;
tuple<int, long, string> current_bat;
tuple<int, float, long, string> current_bat;
const array<string, 10> time_names = {"user", "nice", "system", "idle"};
@ -385,8 +373,8 @@ namespace Cpu {
return core_map;
}
auto get_battery() -> tuple<int, long, string> {
if (not has_battery) return {0, 0, ""};
auto get_battery() -> tuple<int, float, long, string> {
if (not has_battery) return {0, 0, 0, ""};
long seconds = -1;
uint32_t percent = -1;
@ -417,7 +405,7 @@ namespace Cpu {
}
}
return {percent, seconds, status};
return {percent, -1, seconds, status};
}
auto collect(bool no_update) -> cpu_info & {
@ -780,17 +768,6 @@ namespace Net {
bool rescale = true;
uint64_t timestamp = 0;
//* RAII wrapper for getifaddrs
class getifaddr_wrapper {
struct ifaddrs *ifaddr;
public:
int status;
getifaddr_wrapper() { status = getifaddrs(&ifaddr); }
~getifaddr_wrapper() { freeifaddrs(ifaddr); }
auto operator()() -> struct ifaddrs * { return ifaddr; }
};
auto collect(bool no_update) -> net_info & {
auto &net = current_net;
auto &config_iface = Config::getS("net_iface");
@ -800,10 +777,10 @@ namespace Net {
if (not no_update and errors < 3) {
//? Get interface list using getifaddrs() wrapper
getifaddr_wrapper if_wrap{};
if (if_wrap.status != 0) {
IfAddrsPtr if_addrs {};
if (if_addrs.get_status() != 0) {
errors++;
Logger::error("Net::collect() -> getifaddrs() failed with id " + to_string(if_wrap.status));
Logger::error("Net::collect() -> getifaddrs() failed with id " + to_string(if_addrs.get_status()));
redraw = true;
return empty_net;
}
@ -815,7 +792,7 @@ namespace Net {
string ipv4, ipv6;
//? Iteration over all items in getifaddrs() list
for (auto *ifa = if_wrap(); ifa != nullptr; ifa = ifa->ifa_next) {
for (auto *ifa = if_addrs.get(); ifa != nullptr; ifa = ifa->ifa_next) {
if (ifa->ifa_addr == nullptr) continue;
family = ifa->ifa_addr->sa_family;
const auto &iface = ifa->ifa_name;
@ -882,7 +859,7 @@ namespace Net {
}
}
//? Get total recieved and transmitted bytes + device address if no ip was found
//? Get total received and transmitted bytes + device address if no ip was found
for (const auto &iface : interfaces) {
for (const string dir : {"download", "upload"}) {
auto &saved_stat = net.at(iface).stat.at(dir);
@ -1102,8 +1079,8 @@ namespace Proc {
int count = 0;
char buf[_POSIX2_LINE_MAX];
Shared::kvm_openfiles_wrapper kd(nullptr, nullptr, nullptr, KVM_NO_FILES, buf);
const struct kinfo_proc* kprocs = kvm_getprocs(kd(), KERN_PROC_ALL, 0, sizeof(struct kinfo_proc), &count);
Shared::KvmPtr kd {kvm_openfiles(nullptr, nullptr, nullptr, KVM_NO_FILES, buf)};
const struct kinfo_proc* kprocs = kvm_getprocs(kd.get() , KERN_PROC_ALL, 0, sizeof(struct kinfo_proc), &count);
for (int i = 0; i < count; i++) {
const struct kinfo_proc* kproc = &kprocs[i];
@ -1130,7 +1107,7 @@ namespace Proc {
continue;
}
new_proc.name = kproc->p_comm;
char** argv = kvm_getargv(kd(), kproc, 0);
char** argv = kvm_getargv(kd.get(), kproc, 0);
if (argv) {
for (int i = 0; argv[i] and cmp_less(new_proc.cmd.size(), 1000); i++) {
new_proc.cmd += argv[i] + " "s;
@ -1194,18 +1171,13 @@ namespace Proc {
filter_found = 0;
for (auto& p : current_procs) {
if (not tree and not filter.empty()) {
if (not s_contains_ic(to_string(p.pid), filter)
and not s_contains_ic(p.name, filter)
and not s_contains_ic(p.cmd, filter)
and not s_contains_ic(p.user, filter)) {
p.filtered = true;
filter_found++;
}
else {
p.filtered = false;
}
if (!matches_filter(p, filter)) {
p.filtered = true;
filter_found++;
} else {
p.filtered = false;
}
else {
} else {
p.filtered = false;
}
}

View file

@ -191,7 +191,7 @@ namespace Cpu {
string cpuHz;
bool has_battery = true;
bool macM1 = false;
tuple<int, long, string> current_bat;
tuple<int, float, long, string> current_bat;
const array<string, 10> time_names = {"user", "nice", "system", "idle"};
@ -407,8 +407,8 @@ namespace Cpu {
~IOPSList_Wrap() { CFRelease(data); }
};
auto get_battery() -> tuple<int, long, string> {
if (not has_battery) return {0, 0, ""};
auto get_battery() -> tuple<int, float, long, string> {
if (not has_battery) return {0, 0, 0, ""};
uint32_t percent = -1;
long seconds = -1;
@ -447,7 +447,7 @@ namespace Cpu {
has_battery = false;
}
}
return {percent, seconds, status};
return {percent, -1, seconds, status};
}
auto collect(bool no_update) -> cpu_info & {
@ -686,7 +686,7 @@ namespace Mem {
if (host_statistics64(mach_host_self(), HOST_VM_INFO64, (host_info64_t)&p, &info_size) == 0) {
mem.stats.at("free") = p.free_count * Shared::pageSize;
mem.stats.at("cached") = p.external_page_count * Shared::pageSize;
mem.stats.at("used") = (p.active_count + p.inactive_count + p.wire_count) * Shared::pageSize;
mem.stats.at("used") = (p.active_count + p.wire_count) * Shared::pageSize;
mem.stats.at("available") = Shared::totalMem - mem.stats.at("used");
}
@ -940,7 +940,7 @@ namespace Net {
}
}
//? Get total recieved and transmitted bytes + device address if no ip was found
//? Get total received and transmitted bytes + device address if no ip was found
for (const auto &iface : interfaces) {
for (const string dir : {"download", "upload"}) {
auto &saved_stat = net.at(iface).stat.at(dir);
@ -1212,10 +1212,14 @@ namespace Proc {
//? Get program name, command, username, parent pid, nice and status
if (no_cache) {
char fullname[PROC_PIDPATHINFO_MAXSIZE];
proc_pidpath(pid, fullname, sizeof(fullname));
const string f_name = std::string(fullname);
size_t lastSlash = f_name.find_last_of('/');
new_proc.name = f_name.substr(lastSlash + 1);
int rc = proc_pidpath(pid, fullname, sizeof(fullname));
string f_name = "<defunct>";
if (rc != 0) {
f_name = std::string(fullname);
size_t lastSlash = f_name.find_last_of('/');
f_name = f_name.substr(lastSlash + 1);
}
new_proc.name = f_name;
//? Get process arguments if possible, fallback to process path in case of failure
if (Shared::arg_max > 0) {
std::unique_ptr<char[]> proc_chars(new char[Shared::arg_max]);
@ -1245,7 +1249,11 @@ namespace Proc {
new_proc.ppid = kproc.kp_eproc.e_ppid;
new_proc.cpu_s = kproc.kp_proc.p_starttime.tv_sec * 1'000'000 + kproc.kp_proc.p_starttime.tv_usec;
struct passwd *pwd = getpwuid(kproc.kp_eproc.e_ucred.cr_uid);
new_proc.user = pwd->pw_name;
if (pwd != nullptr) {
new_proc.user = pwd->pw_name;
} else {
new_proc.user = std::to_string(kproc.kp_eproc.e_ucred.cr_uid);
}
}
new_proc.p_nice = kproc.kp_proc.p_nice;
new_proc.state = kproc.kp_proc.p_stat;
@ -1297,7 +1305,7 @@ namespace Proc {
filter_found = 0;
for (auto &p : current_procs) {
if (not tree and not filter.empty()) {
if (not s_contains_ic(to_string(p.pid), filter) and not s_contains_ic(p.name, filter) and not s_contains_ic(p.cmd, filter) and not s_contains_ic(p.user, filter)) {
if (!matches_filter(p, filter)) {
p.filtered = true;
filter_found++;
} else {

View file

@ -18,7 +18,7 @@ theme[main_fg]="#cfd8dc"
# Title color for boxes
theme[title]="#ff"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#90"
# Background color of selected item in processes box

View file

@ -18,7 +18,7 @@ theme[main_fg]="#2e3436"
# Title color for boxes
theme[title]="#2e3436"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#1a5fb4"
# Background color of selected item in processes box

View file

@ -18,7 +18,7 @@ theme[main_fg]="#99DFFF"
# Title color for boxes
theme[title]="#99FFFF"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#FF7F00"
# Background color of selected item in processes box

View file

@ -11,7 +11,7 @@ theme[main_fg]="#eee8d5"
# Title color for boxes
theme[title]="#eee8d5"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#d1302c"
# Background color of selected item in processes box

View file

@ -0,0 +1,92 @@
# All graphs and meters can be gradients
# For single color graphs leave "mid" and "end" variable empty.
# Use "start" and "end" variables for two color gradient
# Use "start", "mid" and "end" for three color gradient
# Main background, empty for terminal default, need to be empty if you want transparent background
theme[main_bg]="#2d353b"
# Main text color
theme[main_fg]="#d3c6aa"
# Title color for boxes
theme[title]="#d3c6aa"
# Highlight color for keyboard shortcuts
theme[hi_fg]="#e67e80"
# Background color of selected items
theme[selected_bg]="#3d484d"
# Foreground color of selected items
theme[selected_fg]="#dbbc7f"
# Color of inactive/disabled text
theme[inactive_fg]="#2d353b"
# Color of text appearing on top of graphs, i.e uptime and current network graph scaling
theme[graph_text]="#d3c6aa"
# Misc colors for processes box including mini cpu graphs, details memory graph and details status text
theme[proc_misc]="#a7c080"
# Cpu box outline color
theme[cpu_box]="#3d484d"
# Memory/disks box outline color
theme[mem_box]="#3d484d"
# Net up/down box outline color
theme[net_box]="#3d484d"
# Processes box outline color
theme[proc_box]="#3d484d"
# Box divider line and small boxes line color
theme[div_line]="#3d484d"
# Temperature graph colors
theme[temp_start]="#a7c080"
theme[temp_mid]="#dbbc7f"
theme[temp_end]="#f85552"
# CPU graph colors
theme[cpu_start]="#a7c080"
theme[cpu_mid]="#dbbc7f"
theme[cpu_end]="#f85552"
# Mem/Disk free meter
theme[free_start]="#f85552"
theme[free_mid]="#dbbc7f"
theme[free_end]="#a7c080"
# Mem/Disk cached meter
theme[cached_start]="#7fbbb3"
theme[cached_mid]="#83c092"
theme[cached_end]="#a7c080"
# Mem/Disk available meter
theme[available_start]="#f85552"
theme[available_mid]="#dbbc7f"
theme[available_end]="#a7c080"
# Mem/Disk used meter
theme[used_start]="#a7c080"
theme[used_mid]="#dbbc7f"
theme[used_end]="#f85552"
# Download graph colors
theme[download_start]="#a7c080"
theme[download_mid]="#83c092"
theme[download_end]="#7fbbb3"
# Upload graph colors
theme[upload_start]="#dbbc7f"
theme[upload_mid]="#e69875"
theme[upload_end]="#e67e80"
# Process box color gradient for threads, mem and cpu usage
theme[process_start]="#a7c080"
theme[process_mid]="#e67e80"
theme[process_end]="#f85552"

View file

@ -18,7 +18,7 @@ theme[main_fg]="#737680"
# Title color for boxes
theme[title]="#272a34"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#90"
# Background color of selected item in processes box

View file

@ -18,7 +18,7 @@ theme[main_fg]="#E6E6E6"
# Title color for boxes
theme[title]="#ff"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#90"
# Background color of selected item in processes box

View file

@ -18,7 +18,7 @@ theme[main_fg]="#bb"
# Title color for boxes
theme[title]="#cc"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#90"
# Background color of selected item in processes box

View file

@ -18,7 +18,7 @@ theme[main_fg]="#a89984"
# Title color for boxes
theme[title]="#ebdbb2"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#d79921"
# Background color of selected items

View file

@ -0,0 +1,89 @@
# Btop gruvbox_light theme
# by kk9uk
# Main background, empty for terminal default, need to be empty if you want transparent background
theme[main_bg]="#fbf1c7"
# Main text color
theme[main_fg]="#3c3836"
# Title color for boxes
theme[title]="#3c3836"
# Highlight color for keyboard shortcuts
theme[hi_fg]="#cc241d"
# Background color of selected items
theme[selected_bg]="#f2e5bc"
# Foreground color of selected items
theme[selected_fg]="#8f3f71"
# Color of inactive/disabled text
theme[inactive_fg]="#ebdbb2"
# Color of text appearing on top of graphs, i.e uptime and current network graph scaling
theme[graph_text]="#a89984"
# Misc colors for processes box including mini cpu graphs, details memory graph and details status text
theme[proc_misc]="#98971a"
# Cpu box outline color
theme[cpu_box]="#a89984"
# Memory/disks box outline color
theme[mem_box]="#a89984"
# Net up/down box outline color
theme[net_box]="#a89984"
# Processes box outline color
theme[proc_box]="#a89984"
# Box divider line and small boxes line color
theme[div_line]="#a89984"
# Temperature graph colors
theme[temp_start]="#98971a"
theme[temp_mid]=""
theme[temp_end]="#cc241d"
# CPU graph colors
theme[cpu_start]="#427b58"
theme[cpu_mid]="#d79921"
theme[cpu_end]="#cc241d"
# Mem/Disk free meter
theme[free_start]="#cc241d"
theme[free_mid]="#d79921"
theme[free_end]="#427b58"
# Mem/Disk cached meter
theme[cached_start]="#458588"
theme[cached_mid]="#076678"
theme[cached_end]="#427b58"
# Mem/Disk available meter
theme[available_start]="#cc241d"
theme[available_mid]="#d65d0e"
theme[available_end]="#b57614"
# Mem/Disk used meter
theme[used_start]="#427b58"
theme[used_mid]="#d65d0e"
theme[used_end]="#cc241d"
# Download graph colors
theme[download_start]="#98971a"
theme[download_mid]="#689d6a"
theme[download_end]="#79740e"
# Upload graph colors
theme[upload_start]="#cc241d"
theme[upload_mid]="#d65d0e"
theme[upload_end]="#b57614"
# Process box color gradient for threads, mem and cpu usage
theme[process_start]="#427b58"
theme[process_mid]="#af3a03"
theme[process_end]="#cc241d"

View file

@ -18,7 +18,7 @@ theme[main_fg]="#d4be98"
# Title color for boxes
theme[title]="#d4be98"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#ea6962"
# Background color of selected items

View file

@ -18,7 +18,7 @@ theme[main_fg]="#F8F8F2"
# Title color for boxes
theme[title]="#F8F8F2"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#2eb398"
# Background color of selected item in processes box

View file

@ -18,7 +18,7 @@ theme[main_fg]="#F8F8F2"
# Title color for boxes
theme[title]="#F8F8F2"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#F92672"
# Background color of selected item in processes box

View file

@ -18,7 +18,7 @@ theme[main_fg]="#d6deeb"
# Title color for boxes
theme[title]="#ffffff"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#addb67"
# Background color of selected items

View file

@ -18,7 +18,7 @@ theme[main_fg]="#D8DEE9"
# Title color for boxes
theme[title]="#8FBCBB"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#5E81AC"
# Background color of selected item in processes box

View file

@ -10,7 +10,7 @@ theme[main_fg]="#abb2bf"
# Title color for boxes
theme[title]="#abb2bf"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#61afef"
# Background color of selected item in processes box

View file

@ -12,7 +12,7 @@ theme[main_fg]="#00"
# Title color for boxes
theme[title]="#00"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#CC3E28"
# Background color of selected item in processes box

View file

@ -18,7 +18,7 @@ theme[main_fg]="#eee8d5"
# Title color for boxes
theme[title]="#fdf6e3"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#b58900"
# Background color of selected items

View file

@ -18,7 +18,7 @@ theme[main_fg]="#586e75"
# Title color for boxes
theme[title]="#002b36"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#b58900"
# Background color of selected items

View file

@ -10,7 +10,7 @@ theme[main_fg]="#cfc9c2"
# Title color for boxes
theme[title]="#cfc9c2"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#7dcfff"
# Background color of selected item in processes box

View file

@ -10,7 +10,7 @@ theme[main_fg]="#cfc9c2"
# Title color for boxes
theme[title]="#cfc9c2"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#7dcfff"
# Background color of selected item in processes box

View file

@ -18,7 +18,7 @@ theme[main_fg]="#c5c8c6"
# Title color for boxes
theme[title]="#c5c8c6"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#81beb7"
# Background color of selected item in processes box

View file

@ -18,7 +18,7 @@ theme[main_fg]="#30"
# Title color for boxes
theme[title]="#10"
# Higlight color for keyboard shortcuts
# Highlight color for keyboard shortcuts
theme[hi_fg]="#284d75"
# Background color of selected item in processes box