Compare commits

...

241 Commits

Author SHA1 Message Date
Linus Dierheimer e7474bda1f Adapt to new repository url 2023-07-02 17:04:46 +08:00
李通洲 fa8bfd08f9 Release: v1.12.0 2023-07-02 13:58:11 +08:00
李通洲 11827d64be TerminalShell: fix compiling on macOS 2023-07-02 13:54:31 +08:00
李通洲 47ac01c8e1 Global: fix compiling 2023-07-02 11:10:12 +08:00
李通洲 23c8937362 fix(Shell): fix shell version printing 2023-07-02 11:04:38 +08:00
李通洲 ad3b7762a3 GPU: fix #484 2023-07-02 11:04:38 +08:00
李通洲 b6c5f49650 GPU (Windows): more strict check 2023-07-02 11:04:38 +08:00
李通洲 5b6416e13c CMake (Windows): remove an unused dependency 2023-07-02 11:04:38 +08:00
李通洲 9d4ec4ca65 Bios (macOS): support bios date detection 2023-07-02 11:04:38 +08:00
李通洲 4652002e8c FFPlatform: fix ffPlatformPathAddEnv on Windows 2023-07-02 11:04:38 +08:00
李通洲 2729d72c68 GPU (macOS): remove an unused #include 2023-07-02 11:04:38 +08:00
Carter Li c18bcd316d GPU (macOS): fix typo 2023-07-02 11:04:38 +08:00
Carter Li 8fd30e814a GPU (macOS): fix vendor detection for Intel GPU 2023-07-02 11:04:38 +08:00
李通洲 b1b637fe2f OS (Windows): code refactor; fix common/library.h usage for C++ 2023-07-02 11:04:38 +08:00
李通洲 86806b64a2 CI (FreeBSD): build with libpulse support 2023-07-02 11:04:38 +08:00
Carter Li 96a8548c59 DisplayServer: dirty hack for #477 2023-07-02 11:04:38 +08:00
Carter Li c7becf82bd DisplayServer (Wayland): warn if some properties of wl_output_listener are not supported 2023-07-02 11:04:38 +08:00
李通洲 2d80085d6e Logo (Windows): make Windows logos colorable 2023-07-02 11:04:38 +08:00
Carter Li e63669bea3 Logo: more BSD logos 2023-07-02 11:04:38 +08:00
Carter Li 9568eb8dd3 TerminalFont (FreeBSD): fix gnome-terminal font detection 2023-07-02 11:04:38 +08:00
Carter Li a63925483c Terminal (Linux): print gnome-terminal-server as gnome-terminal 2023-07-02 11:04:38 +08:00
Carter Li 67689f9229 Terminal (FreeBSD): fix Gnome Terminal version detetion on FreeBSD 2023-07-02 11:04:38 +08:00
李通洲 161f86eb45 DisplayServer (Linux): add fast path of kde version detection for Fedora 2023-07-02 11:04:38 +08:00
李通洲 1994219531 DisplayServer (Linux): mark plasmashell --version as slow operation
It costs more than 1 sec some time
2023-07-02 11:04:38 +08:00
李通洲 2ec0353423 Disk (Android): actually detect something 2023-07-02 10:35:33 +08:00
Carter Li 8088905721 Host (macOS): update newest product name data 2023-07-02 10:34:33 +08:00
Carter Li ec049fd490 Fastfetch: set pipe=true automatically if stdout is not a tty 2023-07-02 10:34:12 +08:00
李通洲 033cced5a9 CMake (Windows): silence compiler warnings 2023-07-02 10:32:25 +08:00
李通洲 a059c55f05 Memory (FreeBSD): count cached memory as free memory
As what neofetch did
2023-07-02 10:30:21 +08:00
李通洲 0b00b5ffe0 FreeBSD (CPU): fix temperature detection 2023-07-02 10:29:16 +08:00
李通洲 6e7a6174ba Disk (Linux): don't detect WSL drives as subvolumes 2023-07-02 10:27:36 +08:00
李通洲 07eddf9772 GPU (Linux): always initialize variables 2023-07-02 10:26:32 +08:00
李通洲 c451a377c9 CMake: make some serious warnings as errors 2023-07-02 10:25:41 +08:00
Linus Dierheimer e5de3a90c6 Remove debug statement 2023-07-02 10:24:40 +08:00
Linus Dierheimer 7aecf385e2 Include limits.h when needed
Fixes #472
2023-07-02 10:24:22 +08:00
李通洲 1de049bdf5 Wallpaper (Linux): support Cinnamon 2023-07-02 10:23:00 +08:00
李通洲 55b8c0947b Wallpaper (Linux): support MATE 2023-07-02 10:22:50 +08:00
李通洲 51ba806e6d TerminalFont (Linux): support MATE Terminal 2023-07-02 10:21:51 +08:00
李通洲 ae2855d123 Terminal (Linux): support MATE terminal version detection 2023-07-02 10:21:39 +08:00
李通洲 9000432b52 Wallpaper (Linux): fix xfce wallpaper detection on my laptop 2023-07-02 10:21:28 +08:00
李通洲 618e5f01df Wallpaper (Linux): support lxqt 2023-07-02 10:21:19 +08:00
李通洲 0486ad8da7 TerminalFont (Linux): support QTerminal 2023-07-02 10:21:00 +08:00
李通洲 d23831465a Terminal: support qterminal version detection 2023-07-02 10:20:24 +08:00
李通洲 6ba95d7017 Wallpaper (Linux): support KDE 2023-07-02 10:20:00 +08:00
李通洲 6acfc1b715 DE: fix KDE version detection on Fedora 2023-07-02 10:18:18 +08:00
李通洲 af2e9a9a78 Logo: fix paddingLeft doesn't work when paddingTop is set 2023-07-02 10:17:12 +08:00
李通洲 af33627c4c DisplayServer: fix typos. 2023-07-02 10:13:46 +08:00
Carter Li be60eaf7c8 Merge pull request #468 from LinusDierheimer/dev
Release 1.11.3
2023-06-09 22:34:25 +08:00
李通洲 2235c3e8e4 Release 1.11.3 2023-06-09 22:32:02 +08:00
李通洲 68ae9248a6 Settings: try fixing #467 2023-06-09 22:14:29 +08:00
李通洲 b9742642fc Release 1.11.2 before merging #432 2023-06-09 11:31:36 +08:00
李通洲 356c905703 DisplayServer (macOS): add a missing variable initialization 2023-06-09 11:07:06 +08:00
李通洲 47a5473a35 Init: fix possible memleaks 2023-06-09 10:10:03 +08:00
李通洲 96bca6888a LocalIP: remove useless code 2023-06-09 09:47:45 +08:00
李通洲 bbf31c1a95 Doc: update changelog 2023-06-08 22:28:32 +08:00
李通洲 42b8c1b429 Wallpaper: add missing docs 2023-06-08 22:27:15 +08:00
李通洲 77fde11039 Disk (Linux): fix fastfetch doesn't show Windows drives (/mnt/c) 2023-06-08 22:24:57 +08:00
李通洲 e13f04e80f Disk: backport changes from config branch 2023-06-08 22:24:57 +08:00
李通洲 ad026f6105 LocalIP: backport mac address support
Also change `--*-ip-*` to `--*ip-*` to be consistant to my config branch
2023-06-08 22:22:05 +08:00
李通洲 9107d0e107 Player: try avoiding too Linux-specific names 2023-06-08 16:08:56 +08:00
李通洲 ee876c54bf Theme: split detection code 2023-06-08 16:08:56 +08:00
李通洲 4af44a40bf OS (macOS): add fast path for code name detection 2023-06-07 14:30:45 +08:00
李通洲 399cfe2fbc CI (Wallpaper): run this module 2023-06-06 21:17:03 +08:00
李通洲 71d0cdbfce Wallpaper (Linux): add support for xfce4 2023-06-06 21:02:21 +08:00
李通洲 aae740472f Wallpaper (Linux): add support for gnome 2023-06-06 21:02:21 +08:00
李通洲 8f9beb2789 Wallpaper (macOS): add support 2023-06-06 21:02:21 +08:00
李通洲 77b93a904f Wallpaper (Windows): add new module 2023-06-06 15:48:24 +08:00
李通洲 7934c16bca Doc: update changelog for Icons module 2023-06-06 15:46:57 +08:00
李通洲 941ddee2fc Icons (Windows): add support
Instead of icon theme, this module on Windows detects enabled system icons
2023-06-06 15:35:41 +08:00
李通洲 16113bf330 Icons: split detection code 2023-06-06 15:35:41 +08:00
李通洲 505182428b Global: silence some clang warnings 2023-06-04 01:30:48 +08:00
李通洲 3c2a84ff78 TerminalFont: detect /dev/pts/* 2023-06-01 11:00:40 +08:00
李通洲 8a3346b650 DisplayServer (Wayland): remove a useless line 2023-05-30 22:38:35 +08:00
李通洲 5b63fb1362 Doc: update changelog 2023-05-30 21:04:11 +08:00
李通洲 393857b067 Brightness (Linux): print more useful display name instead of intel_backlight 2023-05-30 20:57:05 +08:00
李通洲 cb8a9c0796 DisplayServer (Wayland): detect display type 2023-05-30 20:54:08 +08:00
李通洲 036752763f DisplayServer (Wayland): silence compiler warnings 2023-05-30 20:53:35 +08:00
李通洲 3a90af1f44 DisplayServer (Wayland): detect screen rotation 2023-05-30 20:16:18 +08:00
李通洲 772de0ff97 DisplayServer: better wayland feature detection 2023-05-29 13:35:45 +08:00
李通洲 53a61a8e58 Display (Linux): support name detection for wayland protocol 2023-05-29 13:30:50 +08:00
Linus Dierheimer a37328c1aa Font: Show QT before GTK
keeps consistency with other modules
2023-05-28 12:34:23 +02:00
李通洲 782325395c DE: Fix Gnome version detection on Fedora 2023-05-28 01:10:00 +08:00
李通洲 e13d554433 Merge remote-tracking branch 'upstream/master' into dev 2023-05-28 00:20:31 +08:00
李通洲 15c72c04af Release: 1.11.1
Update changelog too
2023-05-28 00:17:57 +08:00
李通洲 b797246607 DisplayServer (Apple): use FF_AUTO_FREE 2023-05-28 00:17:57 +08:00
李通洲 d54bb4fd16 Windows: use ffStrbufInitWS 2023-05-28 00:17:57 +08:00
李通洲 0a946e3976 Disk (Windows): improve performance 2023-05-28 00:17:57 +08:00
李通洲 a339f00d83 Windows: fix potential memory curruption bug in unicode.c
Also add ffStrbufInitWS
2023-05-28 00:17:57 +08:00
李通洲 de15866c9a TerminalShell (Windows): print clink version 2023-05-28 00:17:57 +08:00
李通洲 24ee87720e TerminalShell: code refactoring 2023-05-28 00:17:57 +08:00
李通洲 7310b3ed09 TerminalShel (Windows): detect Tabby version with exe file version 2023-05-28 00:17:57 +08:00
李通洲 bb6cdc7bb0 Settings (Linux): fix memleaks reported by LeakSanitizer 2023-05-28 00:17:57 +08:00
李通洲 4a2d20fb74 TerminalFont: support Tabby 2023-05-28 00:17:57 +08:00
李通洲 b136b86300 TerminalShell: support Tabby terminal version detection 2023-05-28 00:17:57 +08:00
李通洲 d4a7ae8b34 Sound (macOS): detecting volume more aggressively 2023-05-28 00:17:57 +08:00
李通洲 04da7cebdb Logo: add macOS small version 2023-05-28 00:17:57 +08:00
李通洲 ccb227e694 TerminalShell: fix iTerm being detected as iTermServer-* sometimes 2023-05-28 00:17:57 +08:00
李通洲 9c7b868227 TerminalShell: support xonsh 2023-05-28 00:17:57 +08:00
李通洲 f333937b35 Swap (Windows): fix compiler warnings 2023-05-28 00:17:57 +08:00
李通洲 e4f6f15d70 Vulkan: try fixing #456 2023-05-28 00:17:57 +08:00
李通洲 5ae8ef1cb3 Swap: split module code from memory.c 2023-05-28 00:17:57 +08:00
李通洲 d863652e1b CMake(Windows): remove USE_WIN_NTAPI option 2023-05-28 00:17:57 +08:00
李通洲 ac540d73b7 Network: drop module 2023-05-28 00:17:57 +08:00
Edward Piper 37b9da7337 Fix EndeavourOS logo again 2023-05-28 00:17:57 +08:00
李通洲 93c0dbde0d DisplayServer (Windows): code simplification 2023-05-28 00:17:57 +08:00
李通洲 aa236b4da0 OpenCL: split detection code 2023-05-28 00:17:57 +08:00
李通洲 2fd3643632 Doc: document Network module 2023-05-28 00:17:57 +08:00
李通洲 24f9247c54 LocalIP: simplify loop interface detection 2023-05-28 00:17:57 +08:00
李通洲 d312b752a1 Network (FreeBSD): add dirty support 2023-05-28 00:17:57 +08:00
李通洲 1b476757a0 Network: code refactor & bug fixes 2023-05-28 00:17:57 +08:00
李通洲 c78a8f6317 Network (Linux): add support 2023-05-28 00:17:57 +08:00
李通洲 24c3788055 Network (Windows): add support 2023-05-28 00:17:57 +08:00
李通洲 a644762a60 Network (macOS): init 2023-05-28 00:17:57 +08:00
Linus Dierheimer 3185d92fb5 --pipe: don't print white color blocks
Fixes #450
2023-05-28 00:17:57 +08:00
李通洲 2c629bc821 FFstrbuf: remove FF_STRBUF_CREATE macro 2023-05-28 00:17:57 +08:00
李通洲 1a6c38bc26 CpuUsage: code refactor 2023-05-28 00:17:57 +08:00
李通洲 589f9aa8f3 Processes: code refactor 2023-05-28 00:17:57 +08:00
tdtooke 70e5d0b235 Update builtin.c 2023-05-28 00:17:57 +08:00
tdtooke aa81d80578 Update builtin.c 2023-05-28 00:17:57 +08:00
KingKrouch 7bc6676680 Update Windows 11 ASCII
Reason being that the original ASCII art as shown in Windows Terminal has random portions using "*" and "(" as opposed to "/".
2023-05-28 00:17:57 +08:00
Linus Dierheimer ab9b10824f Fix flatpak package count
Fix user package count
Show runtime packages too
Fixes #441
2023-05-28 00:17:57 +08:00
Linus Dierheimer f5931e80e7 Fix a new compile warning 2023-05-28 00:17:57 +08:00
Linus Dierheimer bf4f86b4f6 Remove leftover comment 2023-05-28 00:17:57 +08:00
李通洲 7f59f22cf4 Font: code refactor 2023-05-28 00:17:57 +08:00
李通洲 14f4817381 Doc: update changelog 2023-05-28 00:17:57 +08:00
李通洲 e821468bb0 Gamepad: fix copy-and-paste errors 2023-05-28 00:17:57 +08:00
李通洲 d9315d2332 Doc: update changelog 2023-05-28 00:17:57 +08:00
李通洲 a2b4be388e Logo: add SteamOS (#439) 2023-05-28 00:17:57 +08:00
李通洲 35e06642f9 Gamepad (Windows): change the name of Pro Controller 2023-05-28 00:17:57 +08:00
李通洲 92de3e4f30 Windows: fix compiling with imagemagick enabled 2023-05-28 00:17:57 +08:00
李通洲 5b65e182e9 Release: 1.11.1
Update changelog too
2023-05-27 23:53:41 +08:00
李通洲 a7896c39f0 DisplayServer (Apple): use FF_AUTO_FREE 2023-05-27 23:34:04 +08:00
李通洲 4f19bf9a18 Windows: use ffStrbufInitWS 2023-05-27 23:34:03 +08:00
李通洲 c379c65960 Disk (Windows): improve performance 2023-05-27 23:34:03 +08:00
李通洲 1ae0a83880 Windows: fix potential memory curruption bug in unicode.c
Also add ffStrbufInitWS
2023-05-27 23:34:03 +08:00
李通洲 77f7c813f4 TerminalShell (Windows): print clink version 2023-05-27 21:47:36 +08:00
李通洲 bfec8b5634 TerminalShell: code refactoring 2023-05-27 21:47:18 +08:00
李通洲 15a43a6b11 TerminalShel (Windows): detect Tabby version with exe file version 2023-05-27 21:26:00 +08:00
李通洲 c9e3c34ce1 Settings (Linux): fix memleaks reported by LeakSanitizer 2023-05-27 18:25:54 +08:00
李通洲 b99b3ad982 TerminalFont: support Tabby 2023-05-26 15:47:19 +08:00
李通洲 f4ce5c4143 TerminalShell: support Tabby terminal version detection 2023-05-26 15:44:54 +08:00
李通洲 bb4bf63621 Sound (macOS): detecting volume more aggressively 2023-05-26 15:18:59 +08:00
李通洲 60c1a552bb Logo: add macOS small version 2023-05-26 09:16:29 +08:00
李通洲 0a979ddd1e TerminalShell: fix iTerm being detected as iTermServer-* sometimes 2023-05-24 14:50:39 +08:00
李通洲 e45c4b49fd TerminalShell: support xonsh 2023-05-24 14:50:37 +08:00
李通洲 b89ace7aae Swap (Windows): fix compiler warnings 2023-05-16 20:54:45 +08:00
李通洲 424ca923fc Vulkan: try fixing #456 2023-05-16 20:53:45 +08:00
李通洲 e837e1e1d1 Swap: split module code from memory.c 2023-05-11 22:03:18 +08:00
李通洲 aea0986928 CMake(Windows): remove USE_WIN_NTAPI option 2023-05-11 19:55:31 +08:00
李通洲 dc2a3492f0 Network: drop module 2023-05-03 21:50:05 +08:00
Edward Piper 8cf033002c Fix EndeavourOS logo again 2023-05-03 21:49:50 +08:00
李通洲 4d7cb25aa6 DisplayServer (Windows): code simplification 2023-04-26 00:14:39 +08:00
李通洲 60cf3ec861 OpenCL: split detection code 2023-04-25 19:08:27 +08:00
李通洲 4fd82b16e8 Doc: document Network module 2023-04-18 20:59:26 +08:00
李通洲 26feccc0e4 LocalIP: simplify loop interface detection 2023-04-18 20:38:02 +08:00
李通洲 9a1bc66dfc Network (FreeBSD): add dirty support 2023-04-18 20:37:22 +08:00
李通洲 24a3783d7c Network: code refactor & bug fixes 2023-04-18 20:36:41 +08:00
李通洲 7e072c395f Network (Linux): add support 2023-04-18 18:27:25 +08:00
李通洲 94e1ed1d7e Network (Windows): add support 2023-04-18 18:02:31 +08:00
李通洲 94e6f4040d Network (macOS): init 2023-04-18 17:29:48 +08:00
Linus Dierheimer d570e59818 --pipe: don't print white color blocks
Fixes #450
2023-04-17 17:04:28 +02:00
李通洲 0e9d48fff0 FFstrbuf: remove FF_STRBUF_CREATE macro 2023-04-15 12:27:51 +08:00
李通洲 e690d73434 CpuUsage: code refactor 2023-04-15 12:27:51 +08:00
李通洲 8f2b3c6b69 Processes: code refactor 2023-04-15 12:27:51 +08:00
Linus Dierheimer 3c0b2fc910 Merge pull request #448 from LinusDierheimer/master
Merge pull request #437 from LinusDierheimer/dev
2023-04-13 09:17:37 +02:00
Linus Dierheimer 7d0a1c8987 Merge pull request #446 from tdtooke/dev
Adds another font color index to arch icon
2023-04-12 08:09:54 +02:00
tdtooke 757d947446 Update builtin.c 2023-04-11 13:44:07 -07:00
tdtooke 4ced4f9631 Update builtin.c 2023-04-11 13:35:24 -07:00
Linus Dierheimer c6859d7edd Merge pull request #445 from KingKrouch/winlogo-patch
Update Windows 11 ASCII logo to look more visually consistent.
2023-04-10 18:04:17 +02:00
KingKrouch 94cf9a89cc Update Windows 11 ASCII
Reason being that the original ASCII art as shown in Windows Terminal has random portions using "*" and "(" as opposed to "/".
2023-04-10 15:28:42 +00:00
Linus Dierheimer bd8d78427b Fix flatpak package count
Fix user package count
Show runtime packages too
Fixes #441
2023-04-06 11:11:31 +02:00
Linus Dierheimer e40d4b9b68 Fix a new compile warning 2023-04-05 13:41:10 +02:00
Linus Dierheimer 4a07485a19 Remove leftover comment 2023-04-05 13:21:46 +02:00
李通洲 71614e0b0c Font: code refactor 2023-04-04 12:06:21 +08:00
李通洲 d5b6c14bdf Doc: update changelog 2023-04-04 11:05:27 +08:00
李通洲 9509718b0e Gamepad: fix copy-and-paste errors 2023-04-04 11:02:59 +08:00
李通洲 c0ca022ac2 Doc: update changelog 2023-04-02 20:56:12 +08:00
李通洲 708b4a8981 Logo: add SteamOS (#439) 2023-04-02 20:54:16 +08:00
李通洲 8006b0ca4f Gamepad (Windows): change the name of Pro Controller 2023-04-02 20:41:18 +08:00
李通洲 cc2286f056 Windows: fix compiling with imagemagick enabled 2023-04-02 20:41:16 +08:00
Carter Li 81a4be498b Merge pull request #437 from LinusDierheimer/dev
Release 1.11.0
2023-03-25 14:42:07 +08:00
李通洲 56477f5ea6 GPU: be more careful to concat strings 2023-03-25 14:19:58 +08:00
李通洲 ca05e2e905 GPU: add option --gpu-force-vulkan 2023-03-25 13:24:28 +08:00
李通洲 a524302ea7 GPU (Windows): use a faster implementation 2023-03-25 13:04:44 +08:00
李通洲 945b5f1b15 Parsing: make it able to print 1.00 GB 2023-03-25 12:53:08 +08:00
李通洲 ccb0f853db Deps: revert changes of JSON parse library
Let's not make the change before fastfetch 2.0
2023-03-25 10:00:35 +08:00
李通洲 b8f1b0d6aa Release 1.11.0 2023-03-25 01:08:32 +08:00
李通洲 aa7d5bd704 Chore: add myself to FUNDING.yml 2023-03-25 00:50:40 +08:00
李通洲 9ee4c08790 Gamepad (Windows): detect gamepad name by productId
Also improve performance
2023-03-25 00:50:40 +08:00
李通洲 725d2f2612 Windows: fix <Windows.h> header mess 2023-03-25 00:50:40 +08:00
李通洲 4d5ad691f3 Doc: update changelog for flatpak-user support 2023-03-24 23:41:06 +08:00
李通洲 b2f3bf3461 Packages (Linux): support flatpak-user
Fixes #436
2023-03-24 17:47:03 +08:00
李通洲 44c389d29f Doc: document --display-compact-type 2023-03-23 15:09:47 +08:00
李通洲 ac8e03419e DisplayServer (Windows): correct resolution for vertical modes 2023-03-22 23:43:52 +08:00
李通洲 babb836f91 DisplayServer: detect display type ( builtin or external ) 2023-03-22 21:33:46 +08:00
李通洲 95e0a5ee95 DisplayServer: fix programming errors 2023-03-22 20:41:21 +08:00
李通洲 642a0c78cc Display: add options --display-detect-name and --display-precise-refresh-rate 2023-03-22 16:51:06 +08:00
李通洲 1ac90584cb Display: add option --display-compact-mode 2023-03-22 16:19:39 +08:00
李通洲 ccef5de86e Display (macOS, Windows): support display name detection 2023-03-22 16:04:48 +08:00
李通洲 e526ec9c32 Brightness: tidy 2023-03-22 15:44:59 +08:00
李通洲 b15e68658f FFstrbuf: make ffStrbufInit inlinable; add ffStrbufInitMove 2023-03-22 15:35:22 +08:00
李通洲 dcd0f8d3f6 DisplayServer (Windows): support precise refresh rate 2023-03-22 14:59:24 +08:00
李通洲 b3da6b0e89 CPU (Windows): try improving performance 2023-03-21 15:27:34 +08:00
李通洲 ff8c761de0 Doc: add changelog for new cursor features 2023-03-20 14:09:35 +08:00
李通洲 e6258acb55 Cursor (macOS): add support 2023-03-20 14:09:35 +08:00
李通洲 ecafed8fd5 Cursor (Windows): support cursor size detection 2023-03-20 10:29:06 +08:00
李通洲 73f99b1298 Doc: update changelog 2023-03-20 10:18:20 +08:00
Carter Li 7a6ed854ec Merge pull request #435 from regulargvy13/patch-1
Small update for nobara logo
2023-03-18 22:05:36 +08:00
regulargvy13 e923d78016 Small update for nobara logo
The last line in nobara logo was missing just a few spaces, so I added them, and now it's in proper shape :)
2023-03-18 00:46:46 +01:00
李通洲 615b2f72ae GPU (Linux): don't exit if libpci is failed to init
* Fixes #433
* Ref https://github.com/pciutils/pciutils/issues/136
2023-03-13 17:46:24 +08:00
李通洲 9773349253 Chassis: fix wrong module args used when printing 2023-03-10 13:54:27 +08:00
李通洲 fc57fa5415 Doc: document foot terminal support
Fix #431
2023-03-09 14:05:01 +08:00
李通洲 bdd9d46517 TerminalFont: support foot terminal 2023-03-09 14:02:08 +08:00
李通洲 013499f7a2 Terminal: support foot version detection 2023-03-09 14:01:59 +08:00
李通洲 c4416379bb Packages (Linux): support linuxbrew (Homebrew for Linux) 2023-03-08 15:02:58 +08:00
李通洲 c0c07e7dc9 TerminalFont: optimise JSON related code 2023-03-07 00:54:56 +08:00
李通洲 38ec3718ce CI: fix Windows artifacts 2023-03-06 11:22:57 +08:00
李通洲 e2e3561443 TerminalFont: migrate to json-c to prevent from 3rd lib code embedding 2023-03-04 12:17:16 +08:00
李通洲 199f2fc0cd Wifi (Linux): fix compiling with musl (#429) 2023-03-04 09:46:21 +08:00
李通洲 c944b2f599 DateTime: correct format as yyyy-MM-dd 2023-03-04 00:49:07 +08:00
李通洲 fdd0d47762 TerminalFont: migrate cJSON to yyjson
yyjson provides faster JSON parsing and supports JSON with comments ( which is allowed in WT config file )
https://github.com/ibireme/yyjson
2023-03-04 00:47:39 +08:00
李通洲 e5f851dcbb DisplayServer (Windows): fix scaled resolution detection 2023-03-04 00:41:32 +08:00
李通洲 78cb2781e6 Brightness (macOS): display monitor names 2023-03-01 15:40:18 +08:00
李通洲 ef9b5c57b1 DisplayServer (macOS): change process names 2023-02-27 11:29:10 +08:00
Carter Li 52eacd7140 Merge pull request #428 from LinusDierheimer/dev
Release: 1.10.3
2023-02-25 17:34:53 +08:00
李通洲 b19d8d6700 Release: 1.10.3 2023-02-25 16:06:16 +08:00
李通洲 6b0add44ee Init: print threads for --list-features if supported 2023-02-25 15:29:12 +08:00
李通洲 b66338494f CMake: fix compile error on Windows 2023-02-25 13:31:36 +08:00
李通洲 47cec48a49 GPU (Windows): fix uninited variables 2023-02-25 13:31:36 +08:00
李通洲 09ccbca79c WmTheme (Apple): don't depend on displayserver detection 2023-02-25 13:31:36 +08:00
李通洲 4f28ae62a7 Font: don't depend on displayserver detection on Windows and macOS. 2023-02-25 13:31:36 +08:00
李通洲 e953ea6542 Android: enable mutltithreading public-ip / weather detection 2023-02-24 17:48:20 +08:00
李通洲 de72c98a28 Init: don't create detection thread for displayserver on Windows / macOS
Displayserver (mainly resolutions) detection is cheap on win / mac, but creating an detection thread is unnecessary
2023-02-24 17:48:20 +08:00
李通洲 7f15f91bd3 Temps (Windows): dirty support
Note: https://stackoverflow.com/a/17083409
2023-02-23 21:31:33 +08:00
李通洲 c570c5bf97 IO: use FF_AUTO_CLOSE_FD 2023-02-23 13:58:39 +08:00
李通洲 52c304ecae IO (Linux): add detailed error messages for ffProcessAppendStdOut 2023-02-23 13:32:12 +08:00
Carter Li 4f4860eee8 Merge pull request #426 from LinusDierheimer/dev
Release: 1.10.2
2023-02-22 15:58:01 +08:00
李通洲 695e3cc692 Release: 1.10.2 2023-02-22 15:16:54 +08:00
李通洲 e05d9da231 Battery / Wifi: fix missing NULL for ffProcessAppendStdOut 2023-02-22 15:12:37 +08:00
Nanda H Krishna c16f9a9e20 sound_apple.c: handle kAudioObjectPropertyElementMain for macOS < 12 2023-02-22 14:19:22 +08:00
Carter Li 74b1871f18 CI: fix build (#424) 2023-02-21 22:19:17 +08:00
164 changed files with 3047 additions and 1767 deletions
+1 -1
View File
@@ -1 +1 @@
github: LinusDierheimer
github: [LinusDierheimer, CarterLi]
+8 -8
View File
@@ -21,12 +21,12 @@ jobs:
uses: actions/checkout@v3
- name: install required packages
run: sudo apt-get update && sudo apt-get install -y libpci-dev libvulkan-dev libwayland-dev libxrandr-dev libxcb-randr0-dev libdconf-dev libdbus-1-dev libmagickcore-dev libxfconf-0-dev libsqlite3-dev rpm librpm-dev libzstd-dev libegl-dev libglx-dev libosmesa6-dev ocl-icd-opencl-dev libcjson-dev libnm-dev libpulse-dev
run: sudo apt-get update && sudo apt-get install -y libpci-dev libvulkan-dev libwayland-dev libxrandr-dev libxcb-randr0-dev libdconf-dev libdbus-1-dev libmagickcore-dev libxfconf-0-dev libsqlite3-dev rpm librpm-dev libzstd-dev libegl-dev libglx-dev libosmesa6-dev ocl-icd-opencl-dev libnm-dev libpulse-dev libcjson-dev
- name: configure project
env:
CC: ${{ matrix.compiler }}
run: cmake -DCMAKE_BUILD_TYPE=RelWithDebInfo -DENABLE_LIBPCI=${{ matrix.enableFeatures }} -DENABLE_VULKAN=${{ matrix.enableFeatures }} -DENABLE_WAYLAND=${{ matrix.enableFeatures }} -DENABLE_XCB_RANDR=${{ matrix.enableFeatures }} -DENABLE_XCB=${{ matrix.enableFeatures }} -DENABLE_XRANDR=${{ matrix.enableFeatures }} -DENABLE_X11=${{ matrix.enableFeatures }} -DENABLE_GIO=${{ matrix.enableFeatures }} -DENABLE_DCONF=${{ matrix.enableFeatures }} -DENABLE_DBUS=${{ matrix.enableFeatures }} -DENABLE_XFCONF=${{ matrix.enableFeatures }} -DENABLE_SQLITE3=${{ matrix.enableFeatures }} -DENABLE_RPM=${{ matrix.enableFeatures }} -DENABLE_IMAGEMAGICK7=${{ matrix.enableFeatures }} -DENABLE_IMAGEMAGICK6=${{ matrix.enableFeatures }} -DENABLE_CHAFA=${{ matrix.enableFeatures }} -DENABLE_ZLIB=${{ matrix.enableFeatures }} -DENABLE_EGL=${{ matrix.enableFeatures }} -DENABLE_GLX=${{ matrix.enableFeatures }} -DENABLE_OSMESA=${{ matrix.enableFeatures }} -DENABLE_OPENCL=${{ matrix.enableFeatures }} -DENABLE_LIBCJSON=${{ matrix.enableFeatures }} -DENABLE_LIBNM=${{ matrix.enableFeatures }} -DENABLE_PULSE=${{ matrix.enableFeatures }} .
run: cmake -DCMAKE_BUILD_TYPE=RelWithDebInfo -DENABLE_LIBPCI=${{ matrix.enableFeatures }} -DENABLE_VULKAN=${{ matrix.enableFeatures }} -DENABLE_WAYLAND=${{ matrix.enableFeatures }} -DENABLE_XCB_RANDR=${{ matrix.enableFeatures }} -DENABLE_XCB=${{ matrix.enableFeatures }} -DENABLE_XRANDR=${{ matrix.enableFeatures }} -DENABLE_X11=${{ matrix.enableFeatures }} -DENABLE_GIO=${{ matrix.enableFeatures }} -DENABLE_DCONF=${{ matrix.enableFeatures }} -DENABLE_DBUS=${{ matrix.enableFeatures }} -DENABLE_XFCONF=${{ matrix.enableFeatures }} -DENABLE_SQLITE3=${{ matrix.enableFeatures }} -DENABLE_RPM=${{ matrix.enableFeatures }} -DENABLE_IMAGEMAGICK7=${{ matrix.enableFeatures }} -DENABLE_IMAGEMAGICK6=${{ matrix.enableFeatures }} -DENABLE_CHAFA=${{ matrix.enableFeatures }} -DENABLE_ZLIB=${{ matrix.enableFeatures }} -DENABLE_EGL=${{ matrix.enableFeatures }} -DENABLE_GLX=${{ matrix.enableFeatures }} -DENABLE_OSMESA=${{ matrix.enableFeatures }} -DENABLE_OPENCL=${{ matrix.enableFeatures }} -DENABLE_LIBNM=${{ matrix.enableFeatures }} -DENABLE_PULSE=${{ matrix.enableFeatures }} -DENABLE_JSONC=${{ matrix.enableFeatures }} .
- name: build project
run: cmake --build .
@@ -53,7 +53,7 @@ jobs:
uses: actions/checkout@v3
- name: install required packages
run: sudo apt-get update && sudo apt-get install -y libpci-dev libvulkan-dev libwayland-dev libxrandr-dev libxcb-randr0-dev libdconf-dev libdbus-1-dev libmagickcore-dev libxfconf-0-dev libsqlite3-dev rpm librpm-dev libzstd-dev libegl-dev libglx-dev libosmesa6-dev ocl-icd-opencl-dev libcjson-dev libnm-dev libpulse-dev
run: sudo apt-get update && sudo apt-get install -y libpci-dev libvulkan-dev libwayland-dev libxrandr-dev libxcb-randr0-dev libdconf-dev libdbus-1-dev libmagickcore-dev libxfconf-0-dev libsqlite3-dev rpm librpm-dev libzstd-dev libegl-dev libglx-dev libosmesa6-dev ocl-icd-opencl-dev libnm-dev libpulse-dev libcjson-dev
- name: Initialize CodeQL
uses: github/codeql-action/init@v2
@@ -150,7 +150,7 @@ jobs:
uses: vmactions/freebsd-vm@v0
with:
prepare: |
pkg install -y cmake git pkgconf pciutils wayland vulkan-headers vulkan-loader libxcb libXrandr libX11 glib dconf dbus sqlite3-tcl xfce4-conf ImageMagick6 ImageMagick7 chafa egl libosmesa opencl ocl-icd
pkg install -y cmake git pkgconf pciutils wayland vulkan-headers vulkan-loader libxcb libXrandr libX11 glib dconf dbus sqlite3-tcl xfce4-conf ImageMagick6 ImageMagick7 chafa egl libosmesa opencl ocl-icd pulseaudio
run: |
cmake -DSET_TWEAK=Off -DBUILD_TESTS=On .
cmake --build . --target package
@@ -183,7 +183,7 @@ jobs:
with:
msystem: CLANG64
update: true
install: git zip mingw-w64-clang-x86_64-cmake mingw-w64-clang-x86_64-clang mingw-w64-clang-x86_64-cjson mingw-w64-clang-x86_64-vulkan-loader mingw-w64-clang-x86_64-opencl-icd
install: git zip mingw-w64-clang-x86_64-cmake mingw-w64-clang-x86_64-clang mingw-w64-clang-x86_64-vulkan-loader mingw-w64-clang-x86_64-opencl-icd mingw-w64-clang-x86_64-cjson
- name: print msys version
run: uname -a
@@ -244,7 +244,7 @@ jobs:
with:
msystem: CLANG32
update: true
install: git zip mingw-w64-clang-i686-cmake mingw-w64-clang-i686-clang mingw-w64-clang-i686-cjson mingw-w64-clang-i686-vulkan-loader mingw-w64-clang-i686-opencl-icd
install: git zip mingw-w64-clang-i686-cmake mingw-w64-clang-i686-clang mingw-w64-clang-i686-vulkan-loader mingw-w64-clang-i686-opencl-icd mingw-w64-clang-i686-cjson
- name: print msys version
run: uname -a
@@ -281,11 +281,11 @@ jobs:
- name: upload artifacts
uses: actions/upload-artifact@v3
with:
name: fastfetch-Win32
name: fastfetch-win32
path: ./fastfetch-*-Win32.zip
release:
if: github.event_name == 'push' && github.ref == 'refs/heads/master' && github.repository == 'LinusDierheimer/fastfetch'
if: github.event_name == 'push' && github.ref == 'refs/heads/master' && github.repository == 'fastfetch-cli/fastfetch'
name: Release
runs-on: ubuntu-latest
needs:
+119
View File
@@ -1,3 +1,122 @@
# 1.12.0
This release backports some changes from dev branch, and fixes 2 crashing issues
Features:
* Support KDE / LXQT / MATE / Cinnamon wallpaper detection (Wallpaper, Linux)
* Support QTerminal version & terminal font detection
* Support MATE Terminal version & terminal font detection
* Set `--pipe true` automatically if stdout is not a tty
* Detect new macs released on WWDC 2023 (macOS, Host)
* Count cached memory as free memory (FreeBSD, Memory)
* Support sound detection (FreeBSD, Sound)
Bugfixes:
* Fix DE detection on Windows 8.1 (Windows, DE)
* Fix `--logo-padding-left` doesn't work when `--logo-padding-top` is set (Logo)
* Fix KDE version detection on Fedora (DE)
* Include limits.h when needed (Linux, #472)
* Fix Windows drives detection in WSL (Linux, Disk)
* Fix CPU temp detection (FreeBSD, CPU)
* Fix disk detection (Android, Disk)
* Fix Gnome Terminal version and font detection (FreeBSD, TerminalFont)
* Fix crash on newer wayland desktops (Linux, Display, #477)
* Fix vendor detection for Intel GPU (macOS, GPU)
* Fix possible crashes on Windows Server (Windows, GPU, #484)
Logo:
* Add bsd, freebsd_small, ghostbsd
* Make Windows 11 logo colorable
# 1.11.3
Bugfixes:
* Fix a segfault bug, regression of `1.11.1` (Linux, wmtheme, #467)
# 1.11.2
This release should be the last version of fastfetch 1.x (if no serious bugs found, hopefully)
Features:
* Support display name, type, rotation detection on Wayland (Linux, Display)
* Print more useful display name instead of intel_backlight (Linux, Brightness)
* Icons module supports Windows (Windows, Icons)
* Add Wallpaper module which shows the current wallpaper image path
* Add mac address detection `--localip-show-mac` (LocalIP, #451)
Bugfixes:
* Fix Gnome version detection on Fedora (DE)
* Fix Windows drives detection in WSL (Disk)
Changes:
* In order to make Icons module consistant between different platforms, `--icons-format` no longer supports individual GTK / QT icon params.
* `--theme-format` no longer supports individual GTK / plasma theme params.
* `--local-ip-*` and `--public-ip-*` have been changed to `--localip-*` and `--publicip-*`
* `--localip-compact-type` is no longer supported. Fastfetch now display IPs as `--localip-compat-type multiline` by default, with `--local-compact true` can be set as an alias of `--localip-compact-type oneline`
* `--localip-v6first` is no longer supported.
# 1.11.1
Features:
* Support xonsh detection (TerminalShell)
* Support Tabby version / terminal font detection (TerminalFont)
Bugfixes:
* Fix name of Pro Controller (Gamepad, Windows)
* Fix compile error with imagemagick enabled (Windows)
* Fix copy-and-paste errors (Gamepad)
* Flatpak: Fix user package count
* Flatpak: Count runtime packages too (#441)
* Fix flatpak package count (#441)
* Don't print white color blocks with `--pipe` (#450)
* Fix iTerm being detected as iTermServer-* sometimes
* Fix sound device volume being incorrectly detected as muted sometimes (Sound)
* Fix memleaks reported by LeakSanitizer (Linux)
* Fix potential memory curruption bug in unicode.c (Windows)
Logo:
* Update Windows 11 ASCII logo to look more visually consistent (#445)
* Add another font color index to arch icon (#446)
* Add SteamOS
* Add macOS small / small2
# 1.11.0
Features:
* Support linuxbrew (Packages, Linux)
* Support foot terminal (#431, Linux)
* Support cursor size detection on Windows (Cursor, Windows)
* Support cursor detection on macOS (Cursor, macOS)
* Support display name, display type and decimal refresh rate detection (Display, macOS / Windows)
* Support `--display-compact-type` to display multiple resolutions in one line (Display)
* Support flatpak-user (Packages, Linux, #436)
* Support `--gpu-force-vulkan` to force using vulkan to detect GPUs, which support video memory usage detection with `--allow-slow-operations` (GPU)
Bugfixes:
* Fix date time format
* Fix compiling with musl (Wifi, Linux, #429)
* Don't exit if libpci is failed to init (GPU, Linux, #433)
* Names of most well-known gamepads are correctly printed instead of `Wireless Controller` on Windows
Logo:
* Small update for nobara logo (#435, @regulargvy13)
# 1.10.3
Bugfixes:
* Fix uninitialized variables (GPU, Windows)
* Fix compiling errors (Windows)
Improvements:
* Improve preformance (WmTheme amd Font, Windows and macOS)
* Enable nonblocking public-ip / weather detection (Android)
# 1.10.2
Bugfixes:
* Handle `kAudioObjectPropertyElementMain` for macOS **SDK** < 12 (#425, @nandahkrishna)
* Add missing `NULL` for `ffProcessAppendStdOut` (#421)
# 1.10.1
New release for debugging #421
+55 -31
View File
@@ -1,10 +1,10 @@
cmake_minimum_required(VERSION 3.12.0) # target_link_libraries with OBJECT libs & project homepage url
project(fastfetch
VERSION 1.10.1
VERSION 1.12.0
LANGUAGES C
DESCRIPTION "Fast system information tool"
HOMEPAGE_URL "https://github.com/LinusDierheimer/fastfetch"
HOMEPAGE_URL "https://github.com/fastfetch-cli/fastfetch"
)
set(PROJECT_LICENSE "MIT license")
@@ -57,7 +57,7 @@ cmake_dependent_option(ENABLE_GIO "Enable gio-2.0" ON "LINUX OR BSD" OFF)
cmake_dependent_option(ENABLE_DCONF "Enable dconf" ON "LINUX OR BSD" OFF)
cmake_dependent_option(ENABLE_DBUS "Enable dbus-1" ON "LINUX OR BSD" OFF)
cmake_dependent_option(ENABLE_XFCONF "Enable libxfconf-0" ON "LINUX OR BSD" OFF)
cmake_dependent_option(ENABLE_SQLITE3 "Enable sqlite3" ON "LINUX OR BSD" OFF)
cmake_dependent_option(ENABLE_SQLITE3 "Enable sqlite3" ON "LINUX OR BSD OR APPLE" OFF)
cmake_dependent_option(ENABLE_RPM "Enable rpm" ON "LINUX" OFF)
cmake_dependent_option(ENABLE_IMAGEMAGICK7 "Enable imagemagick 7" ON "LINUX OR BSD OR APPLE OR WIN32" OFF)
cmake_dependent_option(ENABLE_IMAGEMAGICK6 "Enable imagemagick 6" ON "LINUX OR BSD OR APPLE" OFF)
@@ -67,13 +67,12 @@ cmake_dependent_option(ENABLE_EGL "Enable egl" ON "LINUX OR BSD" OFF)
cmake_dependent_option(ENABLE_GLX "Enable glx" ON "LINUX OR BSD" OFF)
cmake_dependent_option(ENABLE_OSMESA "Enable osmesa" ON "LINUX OR BSD" OFF)
cmake_dependent_option(ENABLE_OPENCL "Enable opencl" ON "LINUX OR BSD OR WIN32" OFF)
cmake_dependent_option(ENABLE_LIBCJSON "Enable libcjson" ON "LINUX OR WIN32" OFF)
cmake_dependent_option(ENABLE_LIBNM "Enable libnm" ON "LINUX" OFF)
cmake_dependent_option(ENABLE_FREETYPE "Enable freetype" ON "ANDROID" OFF)
cmake_dependent_option(ENABLE_PULSE "Enable pulse" ON "LINUX OR BSD" OFF)
cmake_dependent_option(ENABLE_THREADS "Enable multithreading" ON "Threads_FOUND AND NOT ANDROID" OFF)
cmake_dependent_option(ENABLE_LIBCJSON "Enable libcjson" ON "LINUX OR WIN32" OFF)
cmake_dependent_option(ENABLE_THREADS "Enable multithreading" ON "Threads_FOUND" OFF)
cmake_dependent_option(ENABLE_BUFFER "Enable stdout buffer" ON "LINUX OR APPLE OR BSD OR WIN32 OR ANDROID" OFF)
cmake_dependent_option(USE_WIN_NTAPI "Allow using internal NTAPI" ON "WIN32" OFF)
option(BUILD_TESTS "Build tests" OFF) # Also create test executables
option(SET_TWEAK "Add tweak to project version" ON) # This is set to off by github actions for release builds
@@ -97,12 +96,14 @@ else()
message(STATUS "Threads type: disabled")
endif()
set(WARNING_FLAGS "-Wall -Wextra -Wconversion -Werror=uninitialized -Werror=return-type")
set(CMAKE_C_STANDARD 11)
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -Wextra -Wconversion")
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${WARNING_FLAGS} -Werror=incompatible-pointer-types -Werror=implicit-function-declaration")
if(WIN32)
set(CMAKE_CXX_STANDARD 11)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -Wextra -Wconversion -fno-exceptions -fno-rtti")
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${WARNING_FLAGS} -fno-exceptions -fno-rtti")
set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -Wl,--tsaware -Wl,--build-id -Wl,--subsystem,console:6.1,--major-os-version,6,--minor-os-version,1")
endif()
@@ -117,7 +118,11 @@ if(NOT WIN32)
set(FASTFETCH_FLAGS_DEBUG "${FASTFETCH_FLAGS_DEBUG} -fsanitize=address -fsanitize=undefined")
endif()
set(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} ${FASTFETCH_FLAGS_DEBUG}")
set(CMAKE_EXE_LINKER_FLAGS_DEBUG "${CMAKE_EXE_LINKER_FLAGS_DEBUG} ${FASTFETCH_FLAGS_DEBUG} -rdynamic")
set(CMAKE_EXE_LINKER_FLAGS_DEBUG "${CMAKE_EXE_LINKER_FLAGS_DEBUG} ${FASTFETCH_FLAGS_DEBUG}")
if(NOT WIN32)
set(CMAKE_EXE_LINKER_FLAGS_DEBUG "${CMAKE_EXE_LINKER_FLAGS_DEBUG} -rdynamic")
endif()
if(NOT CMAKE_BUILD_TYPE STREQUAL "Debug")
include(CheckIPOSupported)
@@ -244,6 +249,7 @@ set(LIBFASTFETCH_SRC
src/detection/host/host.c
src/detection/locale/locale.c
src/detection/media/media.c
src/detection/opencl/opencl.c
src/detection/os/os.c
src/detection/packages/packages.c
src/detection/terminalfont/terminalfont.c
@@ -292,6 +298,7 @@ set(LIBFASTFETCH_SRC
src/modules/separator.c
src/modules/shell.c
src/modules/sound.c
src/modules/swap.c
src/modules/media.c
src/modules/terminal.c
src/modules/terminalfont.c
@@ -301,6 +308,7 @@ set(LIBFASTFETCH_SRC
src/modules/uptime.c
src/modules/users.c
src/modules/vulkan.c
src/modules/wallpaper.c
src/modules/weather.c
src/modules/wifi.c
src/modules/wm.c
@@ -337,6 +345,7 @@ if(LINUX)
src/detection/gpu/gpu_linux.c
src/detection/gtk_qt/gtk.c
src/detection/host/host_linux.c
src/detection/icons/icons_linux.c
src/detection/localip/localip_linux.c
src/detection/gamepad/gamepad_linux.c
src/detection/media/media_linux.c
@@ -352,8 +361,10 @@ if(LINUX)
src/detection/temps/temps_linux.c
src/detection/terminalfont/terminalfont_linux.c
src/detection/terminalshell/terminalshell_linux.c
src/detection/theme/theme_linux.c
src/detection/uptime/uptime_linux.c
src/detection/users/users_linux.c
src/detection/wallpaper/wallpaper_linux.c
src/detection/wifi/wifi_linux.c
src/detection/wmtheme/wmtheme_linux.c
src/util/platform/FFPlatform_unix.c
@@ -377,6 +388,7 @@ elseif(ANDROID)
src/detection/font/font_nosupport.c
src/detection/gpu/gpu_nosupport.c
src/detection/host/host_android.c
src/detection/icons/icons_nosupport.c
src/detection/localip/localip_linux.c
src/detection/gamepad/gamepad_nosupport.c
src/detection/media/media_nosupport.c
@@ -391,8 +403,10 @@ elseif(ANDROID)
src/detection/temps/temps_linux.c
src/detection/terminalfont/terminalfont_android.c
src/detection/terminalshell/terminalshell_linux.c
src/detection/theme/theme_nosupport.c
src/detection/uptime/uptime_linux.c
src/detection/users/users_linux.c
src/detection/wallpaper/wallpaper_nosupport.c
src/detection/wifi/wifi_android.c
src/detection/wmtheme/wmtheme_nosupport.c
src/util/platform/FFPlatform_unix.c
@@ -423,6 +437,7 @@ elseif(BSD)
src/detection/gpu/gpu_linux.c
src/detection/gtk_qt/gtk.c
src/detection/host/host_bsd.c
src/detection/icons/icons_linux.c
src/detection/localip/localip_linux.c
src/detection/gamepad/gamepad_nosupport.c
src/detection/media/media_linux.c
@@ -438,8 +453,10 @@ elseif(BSD)
src/detection/temps/temps_linux.c
src/detection/terminalfont/terminalfont_linux.c
src/detection/terminalshell/terminalshell_linux.c
src/detection/theme/theme_linux.c
src/detection/uptime/uptime_bsd.c
src/detection/users/users_linux.c
src/detection/wallpaper/wallpaper_linux.c
src/detection/wifi/wifi_nosupport.c
src/detection/wmtheme/wmtheme_linux.c
src/util/platform/FFPlatform_unix.c
@@ -458,13 +475,14 @@ elseif(APPLE)
src/detection/chassis/chassis_nosupport.c
src/detection/cpu/cpu_apple.c
src/detection/cpuUsage/cpuUsage_apple.c
src/detection/cursor/cursor_nosupport.c
src/detection/cursor/cursor_apple.m
src/detection/disk/disk_apple.m
src/detection/disk/disk_bsd.c
src/detection/displayserver/displayserver_apple.c
src/detection/font/font_apple.m
src/detection/gpu/gpu_apple.c
src/detection/host/host_apple.c
src/detection/icons/icons_nosupport.c
src/detection/localip/localip_linux.c
src/detection/gamepad/gamepad_apple.c
src/detection/media/media_apple.m
@@ -479,8 +497,10 @@ elseif(APPLE)
src/detection/temps/temps_apple.c
src/detection/terminalfont/terminalfont_apple.m
src/detection/terminalshell/terminalshell_linux.c
src/detection/theme/theme_nosupport.c
src/detection/uptime/uptime_bsd.c
src/detection/users/users_linux.c
src/detection/wallpaper/wallpaper_apple.c
src/detection/wifi/wifi_apple.m
src/detection/wmtheme/wmtheme_apple.m
src/util/apple/cf_helpers.c
@@ -504,23 +524,27 @@ elseif(WIN32)
src/detection/disk/disk_windows.c
src/detection/displayserver/displayserver_windows.c
src/detection/font/font_windows.c
src/detection/gpu/gpu_windows.cpp
src/detection/gpu/gpu_windows.c
src/detection/host/host_windows.c
src/detection/icons/icons_windows.c
src/detection/localip/localip_windows.c
src/detection/gamepad/gamepad_windows.cpp
src/detection/gamepad/gamepad_windows.c
src/detection/media/media_nosupport.c
src/detection/memory/memory_windows.c
src/detection/opengl/opengl_windows.c
src/detection/os/os_windows.cpp
src/detection/packages/packages_windows.c
src/detection/poweradapter/poweradapter_nosupport.c
src/detection/processes/processes_windows.cpp
src/detection/processes/processes_windows.c
src/detection/sound/sound_windows.cpp
src/detection/swap/swap_windows.cpp
src/detection/swap/swap_windows.c
src/detection/terminalfont/terminalfont_windows.c
src/detection/terminalshell/terminalshell_windows.cpp
src/detection/terminalshell/terminalshell_windows.c
src/detection/temps/temps_windows.cpp
src/detection/theme/theme_nosupport.c
src/detection/uptime/uptime_windows.c
src/detection/users/users_windows.c
src/detection/wallpaper/wallpaper_windows.c
src/detection/wifi/wifi_windows.c
src/detection/wmtheme/wmtheme_windows.c
src/util/windows/getline.c
@@ -537,6 +561,9 @@ add_library(libfastfetch OBJECT
)
target_compile_definitions(libfastfetch PUBLIC _GNU_SOURCE)
if(WIN32)
target_compile_definitions(libfastfetch PUBLIC WIN32_LEAN_AND_MEAN=1)
endif()
CHECK_INCLUDE_FILE("utmpx.h" HAVE_UTMPX_H)
if(HAVE_UTMPX_H)
@@ -663,10 +690,6 @@ ff_lib_enable(OPENCL
"OpenCL"
"OpenCL"
)
ff_lib_enable(LIBCJSON
"libcjson"
"CJson"
)
ff_lib_enable(LIBNM
"libnm"
"libnm"
@@ -679,6 +702,10 @@ ff_lib_enable(PULSE
"libpulse"
"Pulse"
)
ff_lib_enable(LIBCJSON
"libcjson"
"CJson"
)
if(ENABLE_THREADS)
target_compile_definitions(libfastfetch PRIVATE FF_HAVE_THREADS)
@@ -693,17 +720,19 @@ endif()
if(APPLE)
target_link_libraries(libfastfetch
PRIVATE "-framework Cocoa"
PRIVATE "-framework CoreFoundation"
PRIVATE "-framework CoreAudio"
PRIVATE "-framework CoreVideo"
PRIVATE "-framework CoreWLAN"
PRIVATE "-framework IOBluetooth"
PRIVATE "-framework IOKit"
PRIVATE "-framework OpenGL"
PRIVATE "-framework OpenCL"
PRIVATE "-framework Cocoa"
PRIVATE "-framework CoreWLAN"
PRIVATE "-framework CoreAudio"
PRIVATE "-framework CoreVideo"
PRIVATE "-framework IOBluetooth"
PRIVATE "-weak_framework MediaRemote -F /System/Library/PrivateFrameworks"
PRIVATE "-framework SystemConfiguration"
PRIVATE "-weak_framework CoreDisplay"
PRIVATE "-weak_framework DisplayServices -F /System/Library/PrivateFrameworks"
PRIVATE "-weak_framework MediaRemote -F /System/Library/PrivateFrameworks"
)
elseif(WIN32)
target_compile_definitions(libfastfetch PRIVATE -D_WIN32_WINNT=0x0601)
@@ -719,14 +748,9 @@ elseif(WIN32)
PRIVATE "ntdll"
PRIVATE "version"
PRIVATE "setupapi"
PRIVATE "dxgi"
PRIVATE "dinput8"
PRIVATE "hid"
PRIVATE "wtsapi32"
PRIVATE "powrprof"
)
if(USE_WIN_NTAPI)
target_compile_definitions(libfastfetch PRIVATE FF_USE_WIN_NTAPI)
endif()
endif()
target_include_directories(libfastfetch
+5 -4
View File
@@ -10,7 +10,7 @@ Fastfetch is a [neofetch](https://github.com/dylanaraps/neofetch)-like tool for
<img src="screenshots/example3.png" width="48%" align="top" />
<img src="screenshots/example5.png" height="15%" align="top" />
There are [screenshots on different platforms](https://github.com/LinusDierheimer/fastfetch/wiki)
There are [screenshots on different platforms](https://github.com/fastfetch-cli/fastfetch/wiki)
## Customization
@@ -64,6 +64,7 @@ The following libraries are used if present at runtime:
* [`MoltenVK`](https://github.com/KhronosGroup/MoltenVK): Vulkan driver for macOS. [`molten-vk`](https://github.com/Homebrew/homebrew-core/blob/HEAD/Formula/molten-vk.rb)
* [`libmagickcore` (ImageMagick)](https://www.imagemagick.org/): Images in terminal using sixel graphics protocol. [`imagemagick`](https://github.com/Homebrew/homebrew-core/blob/HEAD/Formula/imagemagick.rb)
* [`libchafa`](https://github.com/hpjansson/chafa): Image output as ascii art. [`chafa`](https://github.com/Homebrew/homebrew-core/blob/HEAD/Formula/chafa.rb)
* [`libsqlite3`](https://www.sqlite.org/index.html): Used for fast wallpaper detection ( fallback to AppleScript )
For the image logo, iTerm with iterm image protocol should work. Apple Terminal is not supported.
@@ -89,12 +90,12 @@ All categories not listed here should work without needing a specific implementa
##### Available Modules
```
Battery, Bios, Bluetooth, Board, Break, Brightness, Colors, Command, CPU, CPUUsage, Cursor, Custom, Date, DateTime, DE, Disk, Display, Font, Gamepad, GPU, Host, Icons, Kernel, Locale, LocalIP, Media, Memory, OpenCL, OpenGL, Packages, Player, Power Adapter, Processes, PublicIP, Separator, OS, Shell, Sound, Swap, Terminal, Terminal Font, Theme, Time, Title, Uptime, Vulkan, Wifi, WM, WMTheme
Battery, Bios, Bluetooth, Board, Break, Brightness, Colors, Command, CPU, CPUUsage, Cursor, Custom, Date, DateTime, DE, Disk, Display, Font, Gamepad, GPU, Host, Icons, Kernel, Locale, LocalIP, Media, Memory, OpenCL, OpenGL, Packages, Player, Power Adapter, Processes, PublicIP, Separator, OS, Shell, Sound, Swap, Terminal, Terminal Font, Theme, Time, Title, Uptime, Vulkan, Wallpaper, Wifi, WM, WMTheme
```
##### Builtin logos
```
AlmaLinux, Alpine, Android, Arch, Arco, Artix, Bedrock, CachyOS, CentOS, CRUX, Crystal, Debian, Deepin, Devuan, Endeavour, Enso, Fedora, FreeBSD, Garuda, Gentoo, KDE Neon, KISS, Kubuntu, LangitKetujuh, Linux, MacOS, Manjaro, Mint, MSYS2, NixOS, Nobara, OpenSUSE, OpenSUSE LEAP, OpenSUSE Tumbleweed, Parabola, Pop!_OS, Raspbian, RebornOS, RedstarOS, Rocky, Rosa, Slackware, Solus, Ubuntu, Vanilla, Void, Windows, Windows 11, Windows 8, Zorin
AlmaLinux, Alpine, Android, Arch, Arco, Artix, Bedrock, CachyOS, CentOS, CRUX, Crystal, Debian, Deepin, Devuan, Endeavour, Enso, Fedora, FreeBSD, Garuda, Gentoo, GhostBSD, KDE Neon, KISS, Kubuntu, LangitKetujuh, Linux, MacOS, Manjaro, Mint, MSYS2, NixOS, Nobara, OpenSUSE, OpenSUSE LEAP, OpenSUSE Tumbleweed, Parabola, Pop!_OS, Raspbian, RebornOS, RedstarOS, Rocky, Rosa, Slackware, Solus, SteamOS, Ubuntu, Vanilla, Void, Windows, Windows 11, Windows 8, Zorin
```
##### Package managers
@@ -114,7 +115,7 @@ Budgie, Cinnamon, Gnome, KDE Plasma, LXQt, Mate, XFCE4
##### Terminal fonts
```
Alacritty, Apple Terminal, ConEmu, Deepin Terminal, Gnome Terminal, iTerm2, Kitty, Konsole, LXTerminal, mintty, Terminator, Termux, Tilix, TTY, Warp, WezTerm, Windows Terminal, XFCE4 Terminal
Alacritty, Apple Terminal, ConEmu, Deepin Terminal, foot, Gnome Terminal, iTerm2, Kitty, Konsole, LXTerminal, MATE Terminal, mintty, QTerminal, Tabby, Terminator, Termux, Tilix, TTY, Warp, WezTerm, Windows Terminal, XFCE4 Terminal
```
## Building
+14 -10
View File
@@ -32,8 +32,8 @@ __fastfetch_complete_help()
"battery-format"
"poweradapter-format"
"locale-format"
"local-ip-format"
"public-ip-format"
"localip-format"
"publicip-format"
"player-format"
"media-format"
"datetime-format"
@@ -182,6 +182,8 @@ __fastfetch_completion()
"--cpu-temp"
"--gpu-temp"
"--battery-temp"
"--display-detect-name"
"--display-precise-refresh-rate"
"--localip-show-ipv4"
"--localip-show-ipv6"
"--localip-show-loop"
@@ -199,6 +201,7 @@ __fastfetch_completion()
"--disk-show-subvolumes"
"--gpu-hide-integrated"
"--gpu-hide-discrete"
"--gpu-force-vulkan"
"--disk-show-unknown"
"--bluetooth-show-disconnected"
)
@@ -224,6 +227,7 @@ __fastfetch_completion()
"--color"
"--color-keys"
"--color-title"
"--display-compact-type"
"--separator"
"-s"
"--structure"
@@ -231,8 +235,8 @@ __fastfetch_completion()
"--set-keyless"
"--player-name"
"--percent-type"
"--public-ip-url"
"--public-ip-timeout"
"--publicip-url"
"--publicip-timeout"
"--weather-output-format"
"--weather-timeout"
"--os-key"
@@ -313,12 +317,12 @@ __fastfetch_completion()
"--locale-key"
"--locale-format"
"--locale-error"
"--local-ip-key"
"--local-ip-format"
"--local-ip-error"
"--public-ip-key"
"--public-ip-format"
"--public-ip-error"
"--localip-key"
"--localip-format"
"--localip-error"
"--publicip-key"
"--publicip-format"
"--publicip-error"
"--wifi-key"
"--wifi-format"
"--wifi-error"
+1 -1
View File
@@ -1 +1 @@
--structure Title:Separator:OS:Host:Bios:Board:Chassis:Kernel:Uptime:Processes:Packages:Shell:Display:Brightness:DE:WM:WMTheme:Theme:Icons:Font:Cursor:Terminal:TerminalFont:CPU:CPUUsage:GPU:Memory:Swap:Disk:Battery:PowerAdapter:Player:Media:PublicIP:LocalIP:Wifi:DateTime:Locale:Vulkan:OpenGL:OpenCL:Users:Bluetooth:Sound:Gamepad:Weather:Break:Colors
--structure Title:Separator:OS:Host:Bios:Board:Chassis:Kernel:Uptime:Processes:Packages:Shell:Display:Brightness:DE:WM:WMTheme:Theme:Icons:Font:Cursor:Wallpaper:Terminal:TerminalFont:CPU:CPUUsage:GPU:Memory:Swap:Disk:Battery:PowerAdapter:Player:Media:PublicIP:LocalIP:Wifi:DateTime:Locale:Vulkan:OpenGL:OpenCL:Users:Bluetooth:Sound:Gamepad:Weather:Break:Colors
+1 -1
View File
@@ -3,7 +3,7 @@
--kernel-format Sysname: {}; Release: {}; Version: {}
--uptime-format Days: {}; Hours: {}; Minutes: {}; Seconds: {}
--processes-format Count: {}
--packages-format All: {}; pacman: {}; pacman branch: {}; dpkg: {}; rpm: {}; emerge: {}; eopkg: {}; xbps: {}; apk: {}; flatpak: {}; snap: {}; brew: {}; brew-cask: {}; port: {}; scoop: {}; choco: {}
--packages-format All: {}; pacman: {}; pacman branch: {}; dpkg: {}; rpm: {}; emerge: {}; eopkg: {}; xbps: {}; apk: {}; flatpak-system: {}; flatpak-user: {}; snap: {}; brew: {}; brew-cask: {}; port: {}; scoop: {}; choco: {}
--shell-format Process name: {}; Process path: {}; Process exe: {}; Process version: {}; User path: {}; User exe: {}; User version: {}
--display-format Width: {}; Height: {}; Refresh rate: {}; ScaledWith: {}; ScaledHeight: {}
--de-format Process name: {}; Pretty name: {}; Version: {}
+27 -35
View File
@@ -8,9 +8,8 @@
#include <unistd.h>
#include <sys/stat.h>
#ifdef _WIN32
#include <wincon.h>
#include <windows.h>
#include <locale.h>
#include <shlobj.h>
#include "util/windows/unicode.h"
#else
#include <signal.h>
@@ -61,12 +60,12 @@ static void defaultConfig(FFinstance* instance)
instance->config.showErrors = false;
instance->config.recache = false;
instance->config.allowSlowOperations = false;
instance->config.disableLinewrap = true;
instance->config.hideCursor = true;
instance->config.pipe = !isatty(STDOUT_FILENO);
instance->config.disableLinewrap = !instance->config.pipe;
instance->config.hideCursor = !instance->config.pipe;
instance->config.escapeBedrock = true;
instance->config.binaryPrefixType = FF_BINARY_PREFIX_TYPE_IEC;
instance->config.glType = FF_GL_TYPE_AUTO;
instance->config.pipe = false;
instance->config.multithreading = true;
instance->config.stat = false;
@@ -110,6 +109,7 @@ static void defaultConfig(FFinstance* instance)
initModuleArg(&instance->config.date);
initModuleArg(&instance->config.time);
initModuleArg(&instance->config.vulkan);
initModuleArg(&instance->config.wallpaper);
initModuleArg(&instance->config.openGL);
initModuleArg(&instance->config.openCL);
initModuleArg(&instance->config.users);
@@ -145,6 +145,7 @@ static void defaultConfig(FFinstance* instance)
instance->config.cpuTemp = false;
instance->config.gpuTemp = false;
instance->config.gpuForceVulkan = false;
instance->config.batteryTemp = false;
instance->config.gpuHideIntegrated = false;
@@ -156,10 +157,11 @@ static void defaultConfig(FFinstance* instance)
instance->config.titleFQDN = false;
ffStrbufInitA(&instance->config.diskFolders, 0);
instance->config.diskShowRemovable = true;
instance->config.diskShowHidden = false;
instance->config.diskShowUnknown = false;
instance->config.diskShowSubvolumes = false;
instance->config.diskShowTypes = FF_DISK_TYPE_REGULAR_BIT | FF_DISK_TYPE_EXTERNAL_BIT;
instance->config.displayCompactType = FF_DISPLAY_COMPACT_TYPE_NONE;
instance->config.displayDetectName = false;
instance->config.displayPreciseRefreshRate = false;
instance->config.bluetoothShowDisconnected = false;
@@ -169,12 +171,8 @@ static void defaultConfig(FFinstance* instance)
ffStrbufInitA(&instance->config.separatorString, 0);
instance->config.localIpShowIpV4 = true;
instance->config.localIpShowIpV6 = false;
instance->config.localIpShowLoop = false;
instance->config.localIpV6First = false;
instance->config.localIpShowType = FF_LOCALIP_TYPE_IPV4_BIT;
ffStrbufInit(&instance->config.localIpNamePrefix);
instance->config.localIpCompactType = FF_LOCALIP_COMPACT_TYPE_NONE;
instance->config.publicIpTimeout = 0;
ffStrbufInit(&instance->config.publicIpUrl);
@@ -212,42 +210,29 @@ void ffInitInstance(FFinstance* instance)
defaultConfig(instance);
}
#ifdef FF_HAVE_THREADS
FF_THREAD_ENTRY_DECL_WRAPPER(ffConnectDisplayServer, FFinstance*)
#if !(defined(__APPLE__) || defined(_WIN32))
#if defined(FF_HAVE_THREADS) && !(defined(__APPLE__) || defined(_WIN32) || defined(__ANDROID__))
#include "detection/gtk_qt/gtk_qt.h"
#define FF_DETECT_QT_GTK 1
#define FF_START_DETECTION_THREADS
FF_THREAD_ENTRY_DECL_WRAPPER(ffConnectDisplayServer, FFinstance*)
FF_THREAD_ENTRY_DECL_WRAPPER(ffDetectQt, FFinstance*)
FF_THREAD_ENTRY_DECL_WRAPPER(ffDetectGTK2, FFinstance*)
FF_THREAD_ENTRY_DECL_WRAPPER(ffDetectGTK3, FFinstance*)
FF_THREAD_ENTRY_DECL_WRAPPER(ffDetectGTK4, FFinstance*)
#endif //!(defined(__APPLE__) || defined(_WIN32))
#endif //FF_HAVE_THREADS
void startDetectionThreads(FFinstance* instance)
{
#ifdef FF_HAVE_THREADS
ffThreadDetach(ffThreadCreate(ffConnectDisplayServerThreadMain, instance));
#ifdef FF_DETECT_QT_GTK
ffThreadDetach(ffThreadCreate(ffDetectQtThreadMain, instance));
ffThreadDetach(ffThreadCreate(ffDetectGTK2ThreadMain, instance));
ffThreadDetach(ffThreadCreate(ffDetectGTK3ThreadMain, instance));
ffThreadDetach(ffThreadCreate(ffDetectGTK4ThreadMain, instance));
#endif
#else
FF_UNUSED(instance);
#endif
}
#endif //FF_HAVE_THREADS
static volatile bool ffDisableLinewrap = true;
static volatile bool ffHideCursor = true;
@@ -268,7 +253,7 @@ static void resetConsole()
BOOL WINAPI consoleHandler(DWORD signal)
{
FF_UNUSED(signal);
resetConsole();
resetConsole();
exit(0);
}
#else
@@ -282,8 +267,10 @@ static void exitSignalHandler(int signal)
void ffStart(FFinstance* instance)
{
if(instance->config.multithreading)
startDetectionThreads(instance);
#ifdef FF_START_DETECTION_THREADS
if(instance->config.multithreading)
startDetectionThreads(instance);
#endif
ffDisableLinewrap = instance->config.disableLinewrap && !instance->config.pipe;
ffHideCursor = instance->config.hideCursor && !instance->config.pipe;
@@ -350,6 +337,7 @@ static void destroyConfig(FFinstance* instance)
destroyModuleArg(&instance->config.host);
destroyModuleArg(&instance->config.bios);
destroyModuleArg(&instance->config.board);
destroyModuleArg(&instance->config.chassis);
destroyModuleArg(&instance->config.kernel);
destroyModuleArg(&instance->config.uptime);
destroyModuleArg(&instance->config.processes);
@@ -376,6 +364,7 @@ static void destroyConfig(FFinstance* instance)
destroyModuleArg(&instance->config.locale);
destroyModuleArg(&instance->config.localIP);
destroyModuleArg(&instance->config.publicIP);
destroyModuleArg(&instance->config.wallpaper);
destroyModuleArg(&instance->config.weather);
destroyModuleArg(&instance->config.wifi);
destroyModuleArg(&instance->config.player);
@@ -450,6 +439,9 @@ void ffDestroyInstance(FFinstance* instance)
void ffListFeatures()
{
fputs(
#ifdef FF_HAVE_THREADS
"threads\n"
#endif
#ifdef FF_HAVE_LIBPCI
"libpci\n"
#endif
+30
View File
@@ -7,6 +7,7 @@
#ifdef _WIN32
#include <fileapi.h>
#include <handleapi.h>
#include <io.h>
typedef HANDLE FFNativeFD;
#else
@@ -101,4 +102,33 @@ static inline void ffUnsuppressIO(bool* suppressed)
void ffListFilesRecursively(const char* path);
static inline bool wrapClose(FFNativeFD* pfd)
{
assert(pfd);
#ifndef WIN32
if (*pfd < 0)
return false;
close(*pfd);
#else
// https://devblogs.microsoft.com/oldnewthing/20040302-00/?p=40443
if (*pfd == NULL || *pfd == INVALID_HANDLE_VALUE)
return false;
CloseHandle(*pfd);
#endif
return true;
}
#define FF_AUTO_CLOSE_FD __attribute__((__cleanup__(wrapClose)))
static inline bool wrapFclose(FILE** pfile)
{
assert(pfile);
if (!*pfile)
return false;
fclose(*pfile);
return true;
}
#define FF_AUTO_CLOSE_FILE __attribute__((__cleanup__(wrapFclose)))
#endif // FF_INCLUDED_common_io_io
+6 -18
View File
@@ -27,7 +27,7 @@ bool ffWriteFileData(const char* fileName, size_t dataSize, const void* data)
int openFlagsModes = O_WRONLY | O_CREAT | O_TRUNC;
int openFlagsRights = S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH;
int fd = open(fileName, openFlagsModes, openFlagsRights);
int FF_AUTO_CLOSE_FD fd = open(fileName, openFlagsModes, openFlagsRights);
if(fd == -1)
{
createSubfolders(fileName);
@@ -36,11 +36,7 @@ bool ffWriteFileData(const char* fileName, size_t dataSize, const void* data)
return false;
}
bool ret = write(fd, data, dataSize) != -1;
close(fd);
return ret;
return write(fd, data, dataSize) > 0;
}
bool ffAppendFDBuffer(int fd, FFstrbuf* buffer)
@@ -77,28 +73,20 @@ bool ffAppendFDBuffer(int fd, FFstrbuf* buffer)
ssize_t ffReadFileData(const char* fileName, size_t dataSize, void* data)
{
int fd = open(fileName, O_RDONLY);
int FF_AUTO_CLOSE_FD fd = open(fileName, O_RDONLY);
if(fd == -1)
return -1;
ssize_t readed = ffReadFDData(fd, dataSize, data);
close(fd);
return readed;
return ffReadFDData(fd, dataSize, data);
}
bool ffAppendFileBuffer(const char* fileName, FFstrbuf* buffer)
{
int fd = open(fileName, O_RDONLY);
int FF_AUTO_CLOSE_FD fd = open(fileName, O_RDONLY);
if(fd == -1)
return false;
bool ret = ffAppendFDBuffer(fd, buffer);
close(fd);
return ret;
return ffAppendFDBuffer(fd, buffer);
}
bool ffPathExists(const char* path, FFPathType type)
+7 -21
View File
@@ -2,7 +2,7 @@
static void createSubfolders(const char* fileName)
{
FFstrbuf path;
FF_STRBUF_AUTO_DESTROY path;
ffStrbufInit(&path);
while(*fileName != '\0')
@@ -12,13 +12,11 @@ static void createSubfolders(const char* fileName)
CreateDirectoryA(path.chars, NULL);
++fileName;
}
ffStrbufDestroy(&path);
}
bool ffWriteFileData(const char* fileName, size_t dataSize, const void* data)
{
HANDLE handle = CreateFileA(fileName, GENERIC_WRITE, FILE_SHARE_WRITE, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
HANDLE FF_AUTO_CLOSE_FD handle = CreateFileA(fileName, GENERIC_WRITE, FILE_SHARE_WRITE, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
if(handle == INVALID_HANDLE_VALUE)
{
createSubfolders(fileName);
@@ -28,11 +26,7 @@ bool ffWriteFileData(const char* fileName, size_t dataSize, const void* data)
}
DWORD written;
bool ret = !!WriteFile(handle, data, (DWORD)dataSize, &written, NULL);
CloseHandle(handle);
return ret;
return !!WriteFile(handle, data, (DWORD)dataSize, &written, NULL);
}
bool ffAppendFDBuffer(HANDLE handle, FFstrbuf* buffer)
@@ -69,28 +63,20 @@ bool ffAppendFDBuffer(HANDLE handle, FFstrbuf* buffer)
ssize_t ffReadFileData(const char* fileName, size_t dataSize, void* data)
{
HANDLE handle = CreateFileA(fileName, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
HANDLE FF_AUTO_CLOSE_FD handle = CreateFileA(fileName, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
if(handle == INVALID_HANDLE_VALUE)
return -1;
ssize_t readed = ffReadFDData(handle, dataSize, data);
CloseHandle(handle);
return readed;
return ffReadFDData(handle, dataSize, data);
}
bool ffAppendFileBuffer(const char* fileName, FFstrbuf* buffer)
{
HANDLE handle = CreateFileA(fileName, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
HANDLE FF_AUTO_CLOSE_FD handle = CreateFileA(fileName, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
if(handle == INVALID_HANDLE_VALUE)
return false;
bool ret = ffAppendFDBuffer(handle, buffer);
CloseHandle(handle);
return ret;
return ffAppendFDBuffer(handle, buffer);
}
bool ffPathExists(const char* path, FFPathType type)
+4 -4
View File
@@ -10,7 +10,7 @@
#include <libloaderapi.h>
#define FF_DLOPEN_FLAGS 0
FF_C_NODISCARD static inline void* dlopen(const char* path, int mode) { FF_UNUSED(mode); return LoadLibraryA(path); }
FF_C_NODISCARD static inline void* dlsym(void* handle, const char* symbol) { return GetProcAddress((HMODULE)handle, symbol); }
FF_C_NODISCARD static inline void* dlsym(void* handle, const char* symbol) { return (void*) GetProcAddress((HMODULE)handle, symbol); }
static inline int dlclose(void* handle) { return !FreeLibrary((HMODULE)handle); }
#else
#include <dlfcn.h>
@@ -40,20 +40,20 @@ static inline void ffLibraryUnload(void** handle)
return returnValue;
#define FF_LIBRARY_LOAD_SYMBOL_ADDRESS(library, symbolMapping, symbolName, returnValue) \
symbolMapping = dlsym(library, #symbolName); \
symbolMapping = (__typeof__(&symbolName)) dlsym(library, #symbolName); \
if(symbolMapping == NULL) \
return returnValue;
#define FF_LIBRARY_LOAD_SYMBOL_ADDRESS2(library, symbolMapping, symbolName, alternateName, returnValue) \
symbolMapping = dlsym(library, #symbolName); \
if(symbolMapping == NULL && !(symbolMapping = dlsym(library, #alternateName))) \
if(symbolMapping == NULL && !(symbolMapping = (__typeof__(&symbolName)) dlsym(library, #alternateName))) \
return returnValue;
#define FF_LIBRARY_LOAD_SYMBOL(library, symbolName, returnValue) \
__typeof__(&symbolName) FF_LIBRARY_LOAD_SYMBOL_ADDRESS(library, ff ## symbolName, symbolName, returnValue);
#define FF_LIBRARY_LOAD_SYMBOL_LAZY(library, symbolName) \
__typeof__(&symbolName) ff ## symbolName = dlsym(library, #symbolName);
__typeof__(&symbolName) ff ## symbolName = (__typeof__(&symbolName)) dlsym(library, #symbolName);
#define FF_LIBRARY_LOAD_SYMBOL_MESSAGE(library, symbolName) \
__typeof__(&symbolName) FF_LIBRARY_LOAD_SYMBOL_ADDRESS(library, ff ## symbolName, symbolName, "dlsym " #symbolName " failed");
+1 -1
View File
@@ -65,7 +65,7 @@ static void parseSize(FFstrbuf* result, uint64_t bytes, uint32_t base, uint8_t p
long double size = (long double) bytes;
uint8_t counter = 0;
while(size > base && counter < prefixesLength - 1)
while(size >= base && counter < prefixesLength - 1)
{
size /= base;
counter++;
+2
View File
@@ -3,6 +3,8 @@
#ifndef FF_INCLUDED_parsing_h
#define FF_INCLUDED_parsing_h
#include "fastfetch.h"
#include <stdint.h>
typedef struct FFVersion
+15 -4
View File
@@ -30,9 +30,20 @@ const char* ffProcessAppendStdOut(FFstrbuf* buffer, char* const argv[])
//Parent
close(pipes[1]);
waitpid(childPid, NULL, 0);
bool ok = ffAppendFDBuffer(pipes[0], buffer);
close(pipes[0]);
return ok ? NULL : "ffAppendFDBuffer() failed";
int FF_AUTO_CLOSE_FD childPipeFd = pipes[0];
int status = -1;
if(waitpid(childPid, &status, 0) < 0)
return "waitpid(childPid, &status, 0) failed";
if (!WIFEXITED(status))
return "WIFEXITED(status) == false";
if(WEXITSTATUS(status) == 901)
return "WEXITSTATUS(status) == 901 ( execvp failed )";
if(!ffAppendFDBuffer(childPipeFd, buffer))
return "ffAppendFDBuffer(childPipeFd, buffer) failed";
return NULL;
}
-1
View File
@@ -1,7 +1,6 @@
#include "fastfetch.h"
#include "common/processing.h"
#define WIN32_LEAN_AND_MEAN 1
#include <Windows.h>
const char* ffProcessAppendStdOut(FFstrbuf* buffer, char* const argv[])
+2 -2
View File
@@ -166,10 +166,10 @@ bool ffParsePropFileListValues(const FFlist* list, const char* relativeFile, uin
FFstrbuf baseDir;
ffStrbufInitA(&baseDir, 64);
for(uint32_t i = 0; i < list->length; i++)
FF_LIST_FOR_EACH(FFstrbuf, dirPrefix, *list)
{
//We need to copy the dir each time, because it used by multiple threads, so we can't directly write to it.
ffStrbufSet(&baseDir, ffListGet(list, i));
ffStrbufSet(&baseDir, dirPrefix);
ffStrbufAppendS(&baseDir, relativeFile);
if(ffParsePropFileValues(baseDir.chars, numQueries, queries))
+60 -8
View File
@@ -57,23 +57,31 @@ typedef enum FFInitState
typedef struct GVariantGetters
{
FF_LIBRARY_SYMBOL(g_variant_get_string)
FF_LIBRARY_SYMBOL(g_variant_dup_string)
FF_LIBRARY_SYMBOL(g_variant_get_boolean)
FF_LIBRARY_SYMBOL(g_variant_get_int32)
FF_LIBRARY_SYMBOL(g_variant_unref)
} GVariantGetters;
static FFvariant getGVariantValue(GVariant* variant, FFvarianttype type, const GVariantGetters* variantGetters)
{
FFvariant result;
if(variant == NULL)
return FF_VARIANT_NULL;
result = FF_VARIANT_NULL;
else if(type == FF_VARIANT_TYPE_STRING)
return (FFvariant) {.strValue = variantGetters->ffg_variant_get_string(variant, NULL)};
result = (FFvariant) {.strValue = variantGetters->ffg_variant_dup_string(variant, NULL)}; // Dup string, so that variant itself can be freed
else if(type == FF_VARIANT_TYPE_BOOL)
return (FFvariant) {.boolValue = (bool) variantGetters->ffg_variant_get_boolean(variant), .boolValueSet = true};
result = (FFvariant) {.boolValue = (bool) variantGetters->ffg_variant_get_boolean(variant), .boolValueSet = true};
else if(type == FF_VARIANT_TYPE_INT)
return (FFvariant) {.intValue = variantGetters->ffg_variant_get_int32(variant)};
result = (FFvariant) {.intValue = variantGetters->ffg_variant_get_int32(variant)};
else
return FF_VARIANT_NULL;
result = FF_VARIANT_NULL;
if(variant)
variantGetters->ffg_variant_unref(variant);
return result;
}
typedef struct GSettingsData
@@ -102,9 +110,10 @@ static const GSettingsData* getGSettingsData(const FFinstance* instance)
FF_LIBRARY_DATA_LOAD_SYMBOL(g_settings_schema_source_get_default)
#define data data.variantGetters
FF_LIBRARY_DATA_LOAD_SYMBOL(g_variant_get_string)
FF_LIBRARY_DATA_LOAD_SYMBOL(g_variant_dup_string)
FF_LIBRARY_DATA_LOAD_SYMBOL(g_variant_get_boolean)
FF_LIBRARY_DATA_LOAD_SYMBOL(g_variant_get_int32)
FF_LIBRARY_DATA_LOAD_SYMBOL(g_variant_unref);
#undef data
data.schemaSource = data.ffg_settings_schema_source_get_default();
@@ -169,9 +178,10 @@ static const DConfData* getDConfData(const FFinstance* instance)
FF_LIBRARY_DATA_LOAD_SYMBOL(dconf_client_new)
#define data data.variantGetters
FF_LIBRARY_DATA_LOAD_SYMBOL(g_variant_get_string)
FF_LIBRARY_DATA_LOAD_SYMBOL(g_variant_dup_string)
FF_LIBRARY_DATA_LOAD_SYMBOL(g_variant_get_boolean)
FF_LIBRARY_DATA_LOAD_SYMBOL(g_variant_get_int32)
FF_LIBRARY_DATA_LOAD_SYMBOL(g_variant_unref)
#undef data
data.client = data.ffdconf_client_new();
@@ -288,6 +298,7 @@ typedef struct SQLiteData
FF_LIBRARY_SYMBOL(sqlite3_step)
FF_LIBRARY_SYMBOL(sqlite3_data_count)
FF_LIBRARY_SYMBOL(sqlite3_column_int)
FF_LIBRARY_SYMBOL(sqlite3_column_text)
FF_LIBRARY_SYMBOL(sqlite3_finalize)
FF_LIBRARY_SYMBOL(sqlite3_close)
} SQLiteData;
@@ -301,6 +312,7 @@ static const SQLiteData* getSQLiteData(const FFinstance* instance)
FF_LIBRARY_DATA_LOAD_SYMBOL(sqlite3_step)
FF_LIBRARY_DATA_LOAD_SYMBOL(sqlite3_data_count)
FF_LIBRARY_DATA_LOAD_SYMBOL(sqlite3_column_int)
FF_LIBRARY_DATA_LOAD_SYMBOL(sqlite3_column_text)
FF_LIBRARY_DATA_LOAD_SYMBOL(sqlite3_finalize)
FF_LIBRARY_DATA_LOAD_SYMBOL(sqlite3_close)
@@ -341,12 +353,52 @@ int ffSettingsGetSQLite3Int(const FFinstance* instance, const char* dbPath, cons
return result;
}
bool ffSettingsGetSQLite3String(const FFinstance* instance, const char* dbPath, const char* query, FFstrbuf* result)
{
if(!ffPathExists(dbPath, FF_PATHTYPE_FILE))
return false;
const SQLiteData* data = getSQLiteData(instance);
if(data == NULL)
return false;
sqlite3* db;
if(data->ffsqlite3_open_v2(dbPath, &db, SQLITE_OPEN_READONLY, NULL) != SQLITE_OK)
return false;
sqlite3_stmt* stmt;
if(data->ffsqlite3_prepare_v2(db, query, (int) strlen(query), &stmt, NULL) != SQLITE_OK)
{
data->ffsqlite3_close(db);
return false;
}
if(data->ffsqlite3_step(stmt) != SQLITE_ROW || data->ffsqlite3_data_count(stmt) < 1)
{
data->ffsqlite3_finalize(stmt);
data->ffsqlite3_close(db);
return false;
}
ffStrbufSetS(result, (const char *) data->ffsqlite3_column_text(stmt, 0));
data->ffsqlite3_finalize(stmt);
data->ffsqlite3_close(db);
return true;
}
#else //FF_HAVE_SQLITE3
int ffSettingsGetSQLite3Int(const FFinstance* instance, const char* dbPath, const char* query)
{
FF_UNUSED(instance, dbPath, query)
return 0;
}
bool ffSettingsGetSQLite3String(const FFinstance* instance, const char* dbPath, const char* query, FFstrbuf* result)
{
FF_UNUSED(instance, dbPath, query, result)
return false;
}
#endif //FF_HAVE_SQLITE3
#ifdef __ANDROID__
+1
View File
@@ -31,6 +31,7 @@ FFvariant ffSettingsGet(const FFinstance* instance, const char* dconfKey, const
FFvariant ffSettingsGetXFConf(const FFinstance* instance, const char* channelName, const char* propertyName, FFvarianttype type);
int ffSettingsGetSQLite3Int(const FFinstance* instance, const char* dbPath, const char* query);
bool ffSettingsGetSQLite3String(const FFinstance* instance, const char* dbPath, const char* query, FFstrbuf* result);
#ifdef __ANDROID__
void ffSettingsGetAndroidProperty(const char* propName, FFstrbuf* result);
+1 -1
View File
@@ -20,7 +20,7 @@
}
#define FF_THREAD_ENTRY_DECL_WRAPPER(fn, paramType) static __stdcall unsigned fn ## ThreadMain (void* data) { fn((paramType)data); return 0; }
static inline void ffThreadDetach(FFThreadType thread) { CloseHandle(thread); }
static inline void ffThreadJoin(FFThreadType thread) { WaitForSingleObject(thread, INFINITE); }
static inline void ffThreadJoin(FFThreadType thread) { WaitForSingleObject(thread, 0xffffffff /*INFINITE*/); }
#else
#include <pthread.h>
#define FF_THREAD_MUTEX_INITIALIZER PTHREAD_MUTEX_INITIALIZER
+36 -9
View File
@@ -168,13 +168,13 @@
# Sets the URL of public IP detection server to be used.
# Only HTTP protocol is supported, and the value should not contain "http://" prefix.
# Default is "ipinfo.io/ip".
#--public-ip-url "ipinfo.io/ip"
#--publicip-url "ipinfo.io/ip"
# Public IP timeout option:
# Sets the time to wait for the public ip server to respond.
# Must be a positive integer.
# Default is 0 (disabled).
#--public-ip-timeout 0
#--publicip-timeout 0
# Weather output format option:
# Sets the weather format to be used. It must be URI encoded.
@@ -219,6 +219,13 @@
#--gpu-hide-integrated
#--gpu-hide-discrete
# GPU detection options
# Forces using vulkan to detect GPUs
# which support video memory usage detection with `--allow-slow-operations`
# Must be either true or false
# Default is false.
#--gpu-force-vulkan
# Shell option
# Sets if shell version should be detected and printed
# Must be either true or false
@@ -253,6 +260,24 @@
# Default is false.
#--bluetooth-show-disconnected false
# Display compact output option
# Sets if all displays should be printed in one line
# Must be either original (print pixel resolution) or scaled (print scaled resolution)
# Default is none.
#--display-compact-type none
# Display detect name option
# Sets if display name should be detected and printed (if supported)
# Must be either true of false
# Default is false.
#--display-detect-name none
# Display precise refresh rate option
# Sets if decimal refresh rates should not be rounded into integers when printing
# Must be either true (keep decimals) of false (round into integers)
# Default is false.
#--display-precise-refresh-rate false
# Sound show all option
# Sets if all sound devices should be printed
# Must be either main, active or all. Default is main
@@ -296,8 +321,8 @@
#--battery-key Battery {1}
#--poweradapter-key Power Adapter {1}
#--locale-key Locale
#--local-ip-key Local IP ({1})
#--public-ip-key Public IP
#--localip-key Local IP ({1})
#--publicip-key Public IP
#--wifi-key Wifi
#--weather-key Weather
#--player-key Media Player
@@ -310,6 +335,7 @@
#--bluetooth-key Bluetooth
#--sound-key Sound
#--gamepad-key Gamepad
#--wallpaper-key Wallpaper
# Format options:
# Sets the format string for module values.
@@ -344,8 +370,8 @@
#--battery-format
#--poweradapter-format
#--locale-format
#--local-ip-format
#--public-ip-format
#--localip-format
#--publicip-format
#--weather-format
#--player-format
#--media-format
@@ -357,6 +383,7 @@
#--bluetooth-format
#--sound-format
#--gamepad-format
#--wallpaper-format
# Error options:
# Sets the format string to use if an error occured
@@ -391,8 +418,8 @@
#--battery-error
#--poweradapter-error
#--locale-error
#--local-ip-error
#--public-ip-error
#--localip-error
#--publicip-error
#--weather-error
#--player-error
#--media-error
@@ -404,6 +431,7 @@
#--bluetooth-error
#--sound-error
#--gamepad-error
#--wallpaper-error
# Library options:
# Sets an user specific path to a library to load.
@@ -429,6 +457,5 @@
#--lib-osmesa /usr/lib/libOSMesa.so
#--lib-opencl /usr/lib/libOpenCL.so
#--lib-cjson /usr/lib/libcjson.so
#--lib-cjson /usr/lib/libasound.so
#--lib-freetype /data/data/com.termux/files/usr/lib
#--lib-pulse /usr/lib/libpulse.so
+9 -4
View File
@@ -108,26 +108,31 @@ Module specific options:
--shell-version <?value>: Set if shell version should be detected and printed
--terminal-version <?value>: Set if terminal version should be detected and printed
--disk-folders <folders>: A colon (semicolon on Windows) separated list of folder paths for the disk output. Default is "/:/home" ("C:\\;D:\\ ..." on Windows)
--disk-show-regular <?value>: Set if regular volume should be printed. Default is true
--disk-show-removable <?value>: Set if removable volume should be printed. Default is true
--disk-show-hidden <?value>: Set if hidden volumes should be printed. Default is false
--disk-show-subvolumes <?value>: Set if subvolumes should be printed. Default is false
--disk-show-unknown <?value>: Set if unknown (unable to detect sizes) volumes should be printed. Default is false
--bluetooth-show-disconnected: <?value>: Set if disconnected bluetooth devices should be printed. Default is false
--display-compact-type: <?string>: Set if all displays should be printed in one line. Default is none
--display-detect-name: <?value>: Set if display name should be detected and printed (if supported). Default is false
--display-precise-refresh-rate: <?value>:Set if decimal refresh rates should not be rounded into integers when printing
--sound-type: <value>: Set what type of sound devices should be printed. Should be either main, active or all. Default is main
--battery-dir <folder>: The directory where the battery folders are. Standard: /sys/class/power_supply/
--cpu-temp <?value>: Detect and display CPU temperature if supported. Default is false
--gpu-temp <?value>: Detect and display GPU temperature if supported. Default is false
--gpu-force-vulkan <?value>: Force using vulkan to detect GPUs, which support video memory usage detection with `--allow-slow-operations`. Default is false
--gpu-hide-integrated <?value>: Hide integrated GPU if supported. Default is false
--gpu-hide-discrete <?value>: Hide discrete GPU if supported. Default is false
--battery-temp <?value>: Detect and display Battery temperature if supported. Default is false
--localip-show-ipv4 <?value>: Show IPv4 addresses in local ip module. Default is true
--localip-show-ipv6 <?value>: Show IPv6 addresses in local ip module. Default is false
--localip-show-mac <?value>: Show mac addresses in local ip module. Default is false
--localip-show-loop <?value>: Show loop back addresses (127.0.0.1) in local ip module. Default is false
--localip-name-prefix <str>: Show IPs with given name prefix only. Default is empty
--localip-compact-type <str>: Show IPs in one line. Should be either none, oneline, multiline. Default is none
--localip-v6first <?value>: Set if ipv6 should be printed first. Default is false
--public-ip-timeout: Time in milliseconds to wait for the public ip server to respond. Default is disabled (0)
--public-ip-url: The URL of public IP detection server to be used.
--localip-compact <?value>: Show all IPs in one line. Default is false
--publicip-timeout: Time in milliseconds to wait for the public ip server to respond. Default is disabled (0)
--publicip-url: The URL of public IP detection server to be used.
--weather-timeout: Time in milliseconds to wait for the weather server to respond. Default is disabled (0)
--weather-output-format: The output weather format to be used. It must be URI encoded.
--player-name: The name of the player to use
+2 -1
View File
@@ -14,7 +14,8 @@ const char* ffDetectBatteryImpl(FF_MAYBE_UNUSED FFinstance* instance, FFlist* re
if(ffProcessAppendStdOut(&buffer, (char* const[]){
FF_TERMUX_API_PATH,
FF_TERMUX_API_PARAM
FF_TERMUX_API_PARAM,
NULL
}))
return "Starting `" FF_TERMUX_API_PATH " " FF_TERMUX_API_PARAM "` failed";
+12 -14
View File
@@ -2,24 +2,22 @@
#include "util/windows/unicode.h"
#include "util/mallocHelper.h"
#undef WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <setupapi.h>
#include <batclass.h>
#include <devguid.h>
#include <winternl.h>
#include <powrprof.h>
#ifdef FF_USE_WIN_NTAPI
NTSYSCALLAPI
NTSTATUS
NTAPI
NtPowerInformation(
IN POWER_INFORMATION_LEVEL InformationLevel,
IN PVOID InputBuffer OPTIONAL,
IN ULONG InputBufferLength,
OUT PVOID OutputBuffer OPTIONAL,
IN ULONG OutputBufferLength);
#define CallNtPowerInformation NtPowerInformation
#endif
NTSYSCALLAPI
NTSTATUS
NTAPI
NtPowerInformation(
IN POWER_INFORMATION_LEVEL InformationLevel,
IN PVOID InputBuffer OPTIONAL,
IN ULONG InputBufferLength,
OUT PVOID OutputBuffer OPTIONAL,
IN ULONG OutputBufferLength);
static inline void wrapCloseHandle(HANDLE* handle)
{
@@ -146,7 +144,7 @@ const char* ffDetectBatteryImpl(FFinstance* instance, FFlist* results)
else
{
SYSTEM_BATTERY_STATE info;
if (NT_SUCCESS(CallNtPowerInformation(SystemBatteryState, NULL, 0, &info, sizeof(info))) && info.BatteryPresent)
if (NT_SUCCESS(NtPowerInformation(SystemBatteryState, NULL, 0, &info, sizeof(info))) && info.BatteryPresent)
{
BatteryResult* battery = (BatteryResult*)ffListAdd(results);
ffStrbufInit(&battery->modelName);
+1
View File
@@ -48,6 +48,7 @@ void ffDetectBios(FFBiosResult* bios)
if(IORegistryEntryCreateCFProperties(registryEntry, &properties, kCFAllocatorDefault, kNilOptions) == kIOReturnSuccess)
{
ffCfDictGetString(properties, CFSTR("manufacturer"), &bios->biosVendor);
ffCfDictGetString(properties, CFSTR("time-stamp"), &bios->date);
CFRelease(properties);
}
IOObjectRelease(registryEntry);
@@ -1,6 +1,7 @@
#include "bluetooth.h"
#include "util/windows/unicode.h"
#include <windows.h>
#include <bluetoothapis.h>
#pragma GCC diagnostic push
+22 -4
View File
@@ -1,8 +1,10 @@
#include "brightness.h"
#include "util/apple/cf_helpers.h"
#include <CoreGraphics/CoreGraphics.h>
extern int DisplayServicesGetBrightness(CGDirectDisplayID display, float *brightness) __attribute__((weak_import));
extern CFDictionaryRef CoreDisplay_DisplayCreateInfoDictionary(CGDirectDisplayID display) __attribute__((weak_import));
const char* ffDetectBrightness(FFlist* result)
{
@@ -22,11 +24,27 @@ const char* ffDetectBrightness(FFlist* result)
continue;
FFBrightnessResult* display = (FFBrightnessResult*) ffListAdd(result);
if(CGDisplayIsBuiltin(screen))
ffStrbufInitS(&display->name, "built-in");
else
ffStrbufInitF(&display->name, "external-%u", (unsigned) screen);
display->value = brightness * 100;
ffStrbufInit(&display->name);
if(CoreDisplay_DisplayCreateInfoDictionary)
{
CFDictionaryRef FF_CFTYPE_AUTO_RELEASE displayInfo = CoreDisplay_DisplayCreateInfoDictionary(screen);
if(displayInfo)
{
CFDictionaryRef productNames;
if(!ffCfDictGetDict(displayInfo, CFSTR(kDisplayProductName), &productNames))
{
if(!ffCfDictGetString(productNames, CFSTR("en_US"), &display->name))
continue;
}
}
}
if(CGDisplayIsBuiltin(screen))
ffStrbufAppendS(&display->name, "built-in");
else
ffStrbufAppendF(&display->name, "external-%u", (unsigned) screen);
}
return NULL;
+17 -7
View File
@@ -2,6 +2,8 @@
#include "common/io/io.h"
#include <dirent.h>
#include <ctype.h>
#include <limits.h>
const char* ffDetectBrightness(FF_MAYBE_UNUSED FFlist* result)
{
@@ -12,13 +14,13 @@ const char* ffDetectBrightness(FF_MAYBE_UNUSED FFlist* result)
if(dirp == NULL)
return "Failed to open `/sys/class/backlight/`";
FFstrbuf backlightDir;
FF_STRBUF_AUTO_DESTROY backlightDir;
ffStrbufInitA(&backlightDir, 64);
ffStrbufAppendS(&backlightDir, backlightDirPath);
uint32_t backlightDirLength = backlightDir.length;
FFstrbuf buffer;
FF_STRBUF_AUTO_DESTROY buffer;
ffStrbufInit(&buffer);
struct dirent* entry;
@@ -38,18 +40,26 @@ const char* ffDetectBrightness(FF_MAYBE_UNUSED FFlist* result)
if(ffReadFileBuffer(backlightDir.chars, &buffer))
{
FFBrightnessResult* display = (FFBrightnessResult*) ffListAdd(result);
ffStrbufInitS(&display->name, entry->d_name);
ffStrbufSubstrBeforeLastC(&backlightDir, '/');
ffStrbufAppendS(&backlightDir, "/device");
ffStrbufInitA(&display->name, PATH_MAX + 1);
if(realpath(backlightDir.chars, display->name.chars))
{
ffStrbufRecalculateLength(&display->name);
ffStrbufSubstrAfterLastC(&display->name, '/');
if(ffStrbufStartsWithS(&display->name, "card") && isdigit(display->name.chars[4]))
ffStrbufSubstrAfterFirstC(&display->name, '-');
}
else
ffStrbufInitS(&display->name, entry->d_name);
double maxBrightness = ffStrbufToDouble(&buffer);
display->value = (float) (actualBrightness * 100 / maxBrightness);
}
break;
}
ffStrbufSubstrBefore(&backlightDir, backlightDirLength);
}
closedir(dirp);
ffStrbufDestroy(&backlightDir);
ffStrbufDestroy(&buffer);
return NULL;
}
+2 -3
View File
@@ -7,9 +7,8 @@ void ffDetectCPUImpl(const FFinstance* instance, FFCPUResult* cpu)
if (instance->config.cpuTemp)
{
FFstrbuf cpuTemp;
ffStrbufInit(&cpuTemp);
if(ffSysctlGetString("temperature", &cpuTemp))
FF_STRBUF_AUTO_DESTROY cpuTemp = ffStrbufCreate();
if(ffSysctlGetString("hw.acpi.thermal.tz0.temperature", &cpuTemp))
cpu->temperature = FF_CPU_TEMP_UNSET;
else
cpu->temperature = ffStrbufToDouble(&cpuTemp);
+14 -7
View File
@@ -1,4 +1,5 @@
#include "cpu.h"
#include "detection/temps/temps_windows.h"
#include "util/windows/registry.h"
#include "util/mallocHelper.h"
@@ -14,25 +15,28 @@ void ffDetectCPUImpl(const FFinstance* instance, FFCPUResult* cpu)
{
DWORD length = 0;
GetLogicalProcessorInformationEx(RelationProcessorCore, NULL, &length);
GetLogicalProcessorInformationEx(RelationAll, NULL, &length);
SYSTEM_LOGICAL_PROCESSOR_INFORMATION_EX* FF_AUTO_FREE
pLogicalInfo = (SYSTEM_LOGICAL_PROCESSOR_INFORMATION_EX*)malloc(length);
pProcessorInfo = (SYSTEM_LOGICAL_PROCESSOR_INFORMATION_EX*)malloc(length);
if(pLogicalInfo && GetLogicalProcessorInformationEx(RelationProcessorCore, pLogicalInfo, &length))
if(pProcessorInfo && GetLogicalProcessorInformationEx(RelationAll, pProcessorInfo, &length))
{
for(
SYSTEM_LOGICAL_PROCESSOR_INFORMATION_EX* ptr = pLogicalInfo;
(uint8_t*)ptr < ((uint8_t*)pLogicalInfo) + length;
SYSTEM_LOGICAL_PROCESSOR_INFORMATION_EX* ptr = pProcessorInfo;
(uint8_t*)ptr < ((uint8_t*)pProcessorInfo) + length;
ptr = (SYSTEM_LOGICAL_PROCESSOR_INFORMATION_EX*)(((uint8_t*)ptr) + ptr->Size)
)
{
if(ptr->Relationship == RelationProcessorCore)
++cpu->coresPhysical;
else if(ptr->Relationship == RelationGroup)
{
cpu->coresOnline += ptr->Group.GroupInfo->ActiveProcessorCount;
cpu->coresLogical += ptr->Group.GroupInfo->MaximumProcessorCount;
}
}
}
}
cpu->coresOnline = (uint16_t)GetActiveProcessorCount(ALL_PROCESSOR_GROUPS);
cpu->coresLogical = (uint16_t)GetMaximumProcessorCount(ALL_PROCESSOR_GROUPS);
FF_HKEY_AUTO_DESTROY hKey;
if(!ffRegOpenKeyForRead(HKEY_LOCAL_MACHINE, L"HARDWARE\\DESCRIPTION\\System\\CentralProcessor\\0", &hKey, NULL))
@@ -46,4 +50,7 @@ void ffDetectCPUImpl(const FFinstance* instance, FFCPUResult* cpu)
ffRegReadStrbuf(hKey, L"ProcessorNameString", &cpu->name, NULL);
ffRegReadStrbuf(hKey, L"VendorIdentifier", &cpu->vendor, NULL);
if(instance->config.cpuTemp)
ffDetectSmbiosTemp(&cpu->temperature, NULL);
}
-25
View File
@@ -1,8 +1,6 @@
#include "fastfetch.h"
#include "cpuUsage.h"
#ifdef FF_USE_WIN_NTAPI
#include "util/mallocHelper.h"
#include <ntstatus.h>
@@ -37,26 +35,3 @@ const char* ffGetCpuUsageInfo(uint64_t* inUseAll, uint64_t* totalAll)
return NULL;
}
#else
#include <processthreadsapi.h>
static inline uint64_t fileTimeToUint64(const FILETIME* ft) {
return (((uint64_t)ft->dwHighDateTime) << 32) | ((uint64_t)ft->dwLowDateTime);
}
const char* ffGetCpuUsageInfo(uint64_t* inUseAll, uint64_t* totalAll)
{
FILETIME idleTime, kernelTime, userTime;
if(!GetSystemTimes(&idleTime, &kernelTime, &userTime))
return "GetSystemTimes() failed";
// https://learn.microsoft.com/en-us/windows/win32/api/processthreadsapi/nf-processthreadsapi-getsystemtimes
// `kernelTime` also includes the amount of time the system has been idle.
*totalAll = fileTimeToUint64(&userTime) + fileTimeToUint64(&kernelTime);
*inUseAll = *totalAll - fileTimeToUint64(&idleTime);
return NULL;
}
#endif
+52
View File
@@ -0,0 +1,52 @@
#include "cursor.h"
#import <Foundation/Foundation.h>
static void appendColor(FFstrbuf* str, NSDictionary* color)
{
int r = (int) (((NSNumber*) [color valueForKey:@"red"]).doubleValue * 255);
int g = (int) (((NSNumber*) [color valueForKey:@"green"]).doubleValue * 255);
int b = (int) (((NSNumber*) [color valueForKey:@"blue"]).doubleValue * 255);
int a = (int) (((NSNumber*) [color valueForKey:@"alpha"]).doubleValue * 255);
if (r == 255 && g == 255 && b == 255 && a == 255)
ffStrbufAppendS(str, "White");
else if (r == 0 && g == 0 && b == 0 && a == 255)
ffStrbufAppendS(str, "Black");
else
ffStrbufAppendF(str, "#%02X%02X%02X%02X", r, g, b, a);
}
void ffDetectCursor(const FFinstance* instance, FFCursorResult* result)
{
NSError* error;
NSString* fileName = [NSString stringWithFormat:@"file://%s/Library/Preferences/com.apple.universalaccess.plist", instance->state.platform.homeDir.chars];
NSDictionary* dict = [NSDictionary dictionaryWithContentsOfURL:[NSURL URLWithString:fileName]
error:&error];
if(error)
{
ffStrbufAppendS(&result->error, error.localizedDescription.UTF8String);
return;
}
NSDictionary* color;
ffStrbufAppendS(&result->theme, "Fill - ");
if ((color = [dict valueForKey:@"cursorFill"]))
appendColor(&result->theme, color);
else
ffStrbufAppendS(&result->theme, "Black");
ffStrbufAppendS(&result->theme, ", Outline - ");
if ((color = [dict valueForKey:@"cursorOutline"]))
appendColor(&result->theme, color);
else
ffStrbufAppendS(&result->theme, "White");
NSNumber* mouseDriverCursorSize = [dict valueForKey:@"mouseDriverCursorSize"];
if (mouseDriverCursorSize)
ffStrbufAppendF(&result->size, "%d", (int) (mouseDriverCursorSize.doubleValue * 32));
else
ffStrbufAppendS(&result->size, "32");
}
+19 -12
View File
@@ -1,12 +1,19 @@
#include "cursor.h"
#include "util/windows/registry.h"
void ffDetectCursor(const FFinstance* instance, FFCursorResult* result)
{
FF_UNUSED(instance);
FF_HKEY_AUTO_DESTROY hKey;
if(ffRegOpenKeyForRead(HKEY_CURRENT_USER, L"Control Panel\\Cursors", &hKey, &result->error))
ffRegReadStrbuf(hKey, NULL, &result->theme, &result->error);
}
#include "cursor.h"
#include "util/windows/registry.h"
void ffDetectCursor(const FFinstance* instance, FFCursorResult* result)
{
FF_UNUSED(instance);
FF_HKEY_AUTO_DESTROY hKey;
if(ffRegOpenKeyForRead(HKEY_CURRENT_USER, L"Control Panel\\Cursors", &hKey, &result->error))
{
if (!ffRegReadStrbuf(hKey, NULL, &result->theme, &result->error))
return;
uint32_t cursorBaseSize;
ffRegReadUint(hKey, L"CursorBaseSize", &cursorBaseSize, &result->error);
ffStrbufAppendF(&result->size, "%u", (unsigned) cursorBaseSize);
}
}
+13 -6
View File
@@ -18,11 +18,18 @@ const FFDiskResult* ffDetectDisks()
if(result.disks.length == 0 && result.error.length == 0)
ffStrbufAppendS(&result.error, "No disks found");
//We need to sort the disks, so that we can detect, which disk a path resides on
// For example for /boot/efi/bootmgr we need to check /boot/efi before /boot
//Note that we sort alphabetically here for a better ordering when printing the list,
// so the check must be done in reverse order
ffListSort(&result.disks, compareDisks);
else
{
//We need to sort the disks, so that we can detect, which disk a path resides on
// For example for /boot/efi/bootmgr we need to check /boot/efi before /boot
//Note that we sort alphabetically here for a better ordering when printing the list,
// so the check must be done in reverse order
ffListSort(&result.disks, compareDisks);
FF_LIST_FOR_EACH(FFDisk, disk, result.disks)
{
if(disk->bytesTotal == 0)
disk->type |= FF_DISK_TYPE_UNKNOWN_BIT;
}
}
);
}
-8
View File
@@ -5,14 +5,6 @@
#include "fastfetch.h"
typedef enum FFDiskType
{
FF_DISK_TYPE_REGULAR,
FF_DISK_TYPE_HIDDEN,
FF_DISK_TYPE_EXTERNAL,
FF_DISK_TYPE_SUBVOLUME
} FFDiskType;
typedef struct FFDisk
{
FFstrbuf mountpoint;
+3 -3
View File
@@ -7,11 +7,11 @@ void detectFsInfo(struct statfs* fs, FFDisk* disk)
{
// FreeBSD doesn't support these flags
if(fs->f_flags & MNT_DONTBROWSE)
disk->type = FF_DISK_TYPE_HIDDEN;
disk->type = FF_DISK_TYPE_HIDDEN_BIT;
else if(fs->f_flags & MNT_REMOVABLE)
disk->type = FF_DISK_TYPE_EXTERNAL;
disk->type = FF_DISK_TYPE_EXTERNAL_BIT;
else
disk->type = FF_DISK_TYPE_REGULAR;
disk->type = FF_DISK_TYPE_REGULAR_BIT;
ffStrbufInitS(&disk->name, [NSFileManager.defaultManager displayNameAtPath:@(fs->f_mntonname)].UTF8String);
}
+3 -3
View File
@@ -13,11 +13,11 @@ static void detectFsInfo(struct statfs* fs, FFDisk* disk)
ffStrbufStartsWithS(&disk->mountpoint, "/proc") ||
ffStrbufStartsWithS(&disk->mountpoint, "/zroot")
)
disk->type = FF_DISK_TYPE_HIDDEN;
disk->type = FF_DISK_TYPE_HIDDEN_BIT;
else if((fs->f_flags & MNT_NOSUID) || !(fs->f_flags & MNT_LOCAL))
disk->type = FF_DISK_TYPE_EXTERNAL;
disk->type = FF_DISK_TYPE_EXTERNAL_BIT;
else
disk->type = FF_DISK_TYPE_REGULAR;
disk->type = FF_DISK_TYPE_REGULAR_BIT;
ffStrbufInit(&disk->name);
}
+26 -25
View File
@@ -17,16 +17,7 @@
static bool isPhysicalDevice(FFstrbuf* device)
{
struct stat deviceStat;
if(stat(device->chars, &deviceStat) != 0)
return false;
//Ignore all devices that are not block devices
if(!S_ISBLK(deviceStat.st_mode))
return false;
//Ignore all devices that are not physical devices
#ifndef __ANDROID__ //On Android, `/dev` is not accessable, so that the following checks always fail
//DrvFs is a filesystem plugin to WSL that was designed to support interop between WSL and the Windows filesystem.
if(ffStrbufEqualS(device, "drvfs"))
@@ -36,10 +27,20 @@ static bool isPhysicalDevice(FFstrbuf* device)
if(ffStrbufStartsWithS(device, "rpool/"))
return true;
struct stat deviceStat;
if(stat(device->chars, &deviceStat) != 0)
return false;
//Ignore all devices that are not block devices
if(!S_ISBLK(deviceStat.st_mode))
return false;
//Pseudo filesystems don't have a device in /dev
if(!ffStrbufStartsWithS(device, "/dev/"))
return false;
#endif // __ANDROID__
if(
ffStrbufStartsWithS(device, "/dev/loop") || //Ignore loop devices
ffStrbufStartsWithS(device, "/dev/ram") || //Ignore ram devices
@@ -115,7 +116,7 @@ static void detectName(FFDisk* disk, const FFstrbuf* device)
if(stat(device->chars, &deviceStat) != 0)
return;
FFstrbuf basePath;
FF_STRBUF_AUTO_DESTROY basePath;
ffStrbufInit(&basePath);
//Try partlabel first
@@ -132,8 +133,6 @@ static void detectName(FFDisk* disk, const FFstrbuf* device)
//Use the mountpoint as a last resort
if(disk->name.length == 0)
ffStrbufAppend(&disk->name, &disk->mountpoint);
ffStrbufDestroy(&basePath);
}
#ifdef __ANDROID__
@@ -141,31 +140,34 @@ static void detectName(FFDisk* disk, const FFstrbuf* device)
static void detectType(FF_MAYBE_UNUSED const FFlist* devices, FFDisk* currentDisk, FF_MAYBE_UNUSED const char* options)
{
if(ffStrbufEqualS(&currentDisk->mountpoint, "/") || ffStrbufEqualS(&currentDisk->mountpoint, "/storage/emulated"))
currentDisk->type = FF_DISK_TYPE_REGULAR;
currentDisk->type = FF_DISK_TYPE_REGULAR_BIT;
else if(ffStrbufStartsWithS(&currentDisk->mountpoint, "/mnt/media_rw/"))
currentDisk->type = FF_DISK_TYPE_EXTERNAL;
currentDisk->type = FF_DISK_TYPE_EXTERNAL_BIT;
else
currentDisk->type = FF_DISK_TYPE_HIDDEN;
currentDisk->type = FF_DISK_TYPE_HIDDEN_BIT;
}
#else
static bool isSubvolume(const FFlist* devices)
{
const FFstrbuf* currentDevie = ffListGet(devices, devices->length - 1);
const FFstrbuf* current = ffListGet(devices, devices->length - 1);
if(ffStrbufEqualS(current, "drvfs")) // WSL Windows drives
return false;
//Filter all disks which device was already found. This catches BTRFS subvolumes.
for(uint32_t i = 0; i < devices->length - 1; i++)
{
const FFstrbuf* otherDevice = ffListGet(devices, i);
if(ffStrbufEqual(currentDevie, otherDevice))
if(ffStrbufEqual(current, otherDevice))
return true;
}
//ZFS subvolumes: rpool/<POOL_NAME>/<VOLUME_NAME>/<SUBVOLUME_NAME>.
//Test if the third slash is present.
if(strncmp(currentDevie->chars, "rpool/", 6) == 0 && ffStrHasNChars(currentDevie->chars, '/', 3))
if(ffStrbufStartsWithS(current, "rpool/") && ffStrHasNChars(current->chars, '/', 3))
return true;
return false;
@@ -174,13 +176,13 @@ static bool isSubvolume(const FFlist* devices)
static void detectType(const FFlist* devices, FFDisk* currentDisk, const char* options)
{
if(isSubvolume(devices))
currentDisk->type = FF_DISK_TYPE_SUBVOLUME;
currentDisk->type = FF_DISK_TYPE_SUBVOLUME_BIT;
else if(strstr(options, "nosuid") != NULL || strstr(options, "nodev") != NULL)
currentDisk->type = FF_DISK_TYPE_EXTERNAL;
currentDisk->type = FF_DISK_TYPE_EXTERNAL_BIT;
else if(ffStrbufStartsWithS(&currentDisk->mountpoint, "/boot") || ffStrbufStartsWithS(&currentDisk->mountpoint, "/efi"))
currentDisk->type = FF_DISK_TYPE_HIDDEN;
currentDisk->type = FF_DISK_TYPE_HIDDEN_BIT;
else
currentDisk->type = FF_DISK_TYPE_REGULAR;
currentDisk->type = FF_DISK_TYPE_REGULAR_BIT;
}
#endif
@@ -207,7 +209,7 @@ void ffDetectDisksImpl(FFDiskResult* disks)
return;
}
FFlist devices;
FF_LIST_AUTO_DESTROY devices;
ffListInit(&devices, sizeof(FFstrbuf));
char* line = NULL;
@@ -257,7 +259,6 @@ void ffDetectDisksImpl(FFDiskResult* disks)
FF_LIST_FOR_EACH(FFstrbuf, device, devices)
ffStrbufDestroy(device);
ffListDestroy(&devices);
fclose(mountsFile);
}
+27 -27
View File
@@ -1,36 +1,31 @@
#include "disk.h"
#include "util/windows/unicode.h"
#define WIN32_LEAN_AND_MEAN 1
#include <windows.h>
#include <assert.h>
void ffDetectDisksImpl(FFDiskResult* disks)
{
uint32_t length = GetLogicalDriveStringsA(0, NULL);
if(length == 0)
{
ffStrbufAppendS(&disks->error, "GetLogicalDriveStringsA failed");
return;
}
char* buf = malloc(length + 1);
GetLogicalDriveStringsA(length, buf);
wchar_t buf[MAX_PATH + 1];
uint32_t length = GetLogicalDriveStringsW(sizeof(buf) / sizeof(*buf), buf);
assert(length < sizeof(buf) / sizeof(*buf));
for(uint32_t i = 0; i < length; i++)
{
const char* mountpoint = buf + i;
const wchar_t* mountpoint = buf + i;
UINT driveType = GetDriveTypeA(mountpoint);
UINT driveType = GetDriveTypeW(mountpoint);
if(driveType == DRIVE_NO_ROOT_DIR)
{
i += (uint32_t)strlen(mountpoint);
i += (uint32_t)wcslen(mountpoint);
continue;
}
FFDisk* disk = ffListAdd(&disks->disks);
ffStrbufInitS(&disk->mountpoint, mountpoint);
ffStrbufInitWS(&disk->mountpoint, mountpoint);
uint64_t bytesFree;
if(!GetDiskFreeSpaceExA(mountpoint, NULL, (PULARGE_INTEGER)&disk->bytesTotal, (PULARGE_INTEGER)&bytesFree))
if(!GetDiskFreeSpaceExW(mountpoint, NULL, (PULARGE_INTEGER)&disk->bytesTotal, (PULARGE_INTEGER)&bytesFree))
{
disk->bytesTotal = 0;
bytesFree = 0;
@@ -38,26 +33,33 @@ void ffDetectDisksImpl(FFDiskResult* disks)
disk->bytesUsed = disk->bytesTotal - bytesFree;
if(driveType == DRIVE_REMOVABLE || driveType == DRIVE_REMOTE || driveType == DRIVE_CDROM)
disk->type = FF_DISK_TYPE_EXTERNAL;
disk->type = FF_DISK_TYPE_EXTERNAL_BIT;
else if(driveType == DRIVE_FIXED)
disk->type = FF_DISK_TYPE_REGULAR;
disk->type = FF_DISK_TYPE_REGULAR_BIT;
else
disk->type = FF_DISK_TYPE_HIDDEN;
disk->type = FF_DISK_TYPE_HIDDEN_BIT;
ffStrbufInit(&disk->filesystem);
ffStrbufInit(&disk->name);
wchar_t diskName[MAX_PATH + 1], diskFileSystem[MAX_PATH + 1];
ffStrbufInitA(&disk->filesystem, MAX_PATH + 1);
ffStrbufInitA(&disk->name, MAX_PATH + 1);
//https://learn.microsoft.com/en-us/windows/win32/api/fileapi/nf-fileapi-getvolumeinformationa#remarks
UINT errorMode = SetErrorMode(SEM_FAILCRITICALERRORS);
GetVolumeInformationA(mountpoint,
disk->name.chars, disk->name.allocated, //Volume name
BOOL result = GetVolumeInformationW(mountpoint,
diskName, sizeof(diskName) / sizeof(*diskName), //Volume name
NULL, //Serial number
NULL, //Max component length
NULL, //File system flags
disk->filesystem.chars, disk->filesystem.allocated
diskFileSystem, sizeof(diskFileSystem) / sizeof(*diskFileSystem)
);
SetErrorMode(errorMode);
ffStrbufRecalculateLength(&disk->name);
ffStrbufRecalculateLength(&disk->filesystem);
if(result)
{
ffStrbufSetWS(&disk->filesystem, diskFileSystem);
ffStrbufSetWS(&disk->name, diskName);
}
//TODO: implement
disk->filesUsed = 0;
@@ -65,6 +67,4 @@ void ffDetectDisksImpl(FFDiskResult* disks)
i += disk->mountpoint.length;
}
free(buf);
}
+11 -19
View File
@@ -1,25 +1,15 @@
#include "displayserver.h"
#include "detection/internal.h"
uint32_t ffdsParseRefreshRate(int32_t refreshRate)
{
if(refreshRate <= 0)
return 0;
int remainder = refreshRate % 5;
if(remainder >= 3)
refreshRate += (5 - remainder);
else
refreshRate -= remainder;
//All other typicall refresh rates are dividable by 5
if(refreshRate == 145)
refreshRate = 144;
return (uint32_t) refreshRate;
}
bool ffdsAppendDisplay(FFDisplayServerResult* result, uint32_t width, uint32_t height, uint32_t refreshRate, uint32_t scaledWidth, uint32_t scaledHeight)
bool ffdsAppendDisplay(
FFDisplayServerResult* result,
uint32_t width,
uint32_t height,
double refreshRate,
uint32_t scaledWidth,
uint32_t scaledHeight,
FFstrbuf* name,
FFDisplayType type)
{
if(width == 0 || height == 0)
return false;
@@ -30,6 +20,8 @@ bool ffdsAppendDisplay(FFDisplayServerResult* result, uint32_t width, uint32_t h
display->refreshRate = refreshRate;
display->scaledWidth = scaledWidth;
display->scaledHeight = scaledHeight;
ffStrbufInitMove(&display->name, name);
display->type = type;
return true;
}
+18 -4
View File
@@ -34,13 +34,21 @@
#define FF_WM_PROTOCOL_X11 "X11"
#define FF_WM_PROTOCOL_WAYLAND "Wayland"
typedef enum FFDisplayType {
FF_DISPLAY_TYPE_UNKNOWN,
FF_DISPLAY_TYPE_BUILTIN,
FF_DISPLAY_TYPE_EXTERNAL,
} FFDisplayType;
typedef struct FFDisplayResult
{
uint32_t width;
uint32_t height;
uint32_t refreshRate;
double refreshRate;
uint32_t scaledWidth;
uint32_t scaledHeight;
FFstrbuf name;
FFDisplayType type;
} FFDisplayResult;
typedef struct FFDisplayServerResult
@@ -56,8 +64,14 @@ typedef struct FFDisplayServerResult
const FFDisplayServerResult* ffConnectDisplayServer(const FFinstance* instance);
//Used internal
uint32_t ffdsParseRefreshRate(int32_t refreshRate);
bool ffdsAppendDisplay(FFDisplayServerResult* result, uint32_t width, uint32_t height, uint32_t refreshRate, uint32_t scaledWidth, uint32_t scaledHeight);
bool ffdsAppendDisplay(
FFDisplayServerResult* result,
uint32_t width,
uint32_t height,
double refreshRate,
uint32_t scaledWidth,
uint32_t scaledHeight,
FFstrbuf* name,
FFDisplayType type);
#endif
@@ -1,5 +1,7 @@
#include "displayserver.h"
#include "common/sysctl.h"
#include "util/apple/cf_helpers.h"
#include "util/mallocHelper.h"
#include <stdlib.h>
#include <ctype.h>
@@ -8,7 +10,9 @@
#include <CoreGraphics/CGDirectDisplay.h>
#include <CoreVideo/CVDisplayLink.h>
static void detectDisplays(FFDisplayServerResult* ds)
extern CFDictionaryRef CoreDisplay_DisplayCreateInfoDictionary(CGDirectDisplayID display) __attribute__((weak_import));
static void detectDisplays(FFDisplayServerResult* ds, bool detectName)
{
CGDirectDisplayID screens[128];
uint32_t screenCount;
@@ -36,12 +40,27 @@ static void detectDisplays(FFDisplayServerResult* ds)
}
}
FF_STRBUF_AUTO_DESTROY name;
ffStrbufInit(&name);
if(detectName && CoreDisplay_DisplayCreateInfoDictionary)
{
CFDictionaryRef FF_CFTYPE_AUTO_RELEASE displayInfo = CoreDisplay_DisplayCreateInfoDictionary(screen);
if(displayInfo)
{
CFDictionaryRef productNames;
if(!ffCfDictGetDict(displayInfo, CFSTR(kDisplayProductName), &productNames))
ffCfDictGetString(productNames, CFSTR("en_US"), &name);
}
}
ffdsAppendDisplay(ds,
(uint32_t)CGDisplayModeGetPixelWidth(mode),
(uint32_t)CGDisplayModeGetPixelHeight(mode),
(uint32_t)refreshRate,
refreshRate,
(uint32_t)CGDisplayModeGetWidth(mode),
(uint32_t)CGDisplayModeGetHeight(mode)
(uint32_t)CGDisplayModeGetHeight(mode),
&name,
CGDisplayIsBuiltin(screen) ? FF_DISPLAY_TYPE_BUILTIN : FF_DISPLAY_TYPE_EXTERNAL
);
CGDisplayModeRelease(mode);
}
@@ -55,7 +74,7 @@ static void detectWMPlugin(FFstrbuf* name)
u_int requestLength = sizeof(request) / sizeof(*request);
size_t length = 0;
struct kinfo_proc* processes = ffSysctlGetData(request, requestLength, &length);
FF_AUTO_FREE struct kinfo_proc* processes = ffSysctlGetData(request, requestLength, &length);
if(processes == NULL)
return;
@@ -76,21 +95,20 @@ static void detectWMPlugin(FFstrbuf* name)
name->chars[0] = (char) toupper(name->chars[0]);
break;
}
free(processes);
}
void ffConnectDisplayServerImpl(FFDisplayServerResult* ds, const FFinstance* instance)
{
FF_UNUSED(instance);
ffStrbufInitS(&ds->wmProcessName, "quartz");
ffStrbufInitS(&ds->wmProcessName, "WindowServer");
ffStrbufInitS(&ds->wmPrettyName, "Quartz Compositor");
ffStrbufInit(&ds->wmProtocolName);
if(instance->config.allowSlowOperations)
{
FF_STRBUF_AUTO_DESTROY name;
ffStrbufInit(&name);
detectWMPlugin(&name);
if(name.length)
ffStrbufAppendF(&ds->wmPrettyName, " (with %s)", name.chars);
@@ -99,9 +117,8 @@ void ffConnectDisplayServerImpl(FFDisplayServerResult* ds, const FFinstance* ins
ffStrbufInit(&ds->deProcessName);
ffStrbufInit(&ds->dePrettyName);
ffStrbufInit(&ds->deVersion);
ffStrbufAppendS(&ds->deProcessName, "aqua");
ffStrbufAppendS(&ds->dePrettyName, "Aqua");
ffListInitA(&ds->displays, sizeof(FFDisplayResult), 4);
detectDisplays(ds);
detectDisplays(ds, instance->config.displayDetectName);
}
@@ -1,33 +1,101 @@
#include "displayserver.h"
#include "detection/os/os.h"
#include "util/windows/unicode.h"
#include <dwmapi.h>
#include <WinUser.h>
typedef struct
static void detectDisplays(FFDisplayServerResult* ds, bool detectName)
{
WCHAR* deviceName;
uint32_t width;
uint32_t height;
} DataBundle;
DISPLAYCONFIG_PATH_INFO paths[128];
uint32_t pathCount = sizeof(paths) / sizeof(paths[0]);
DISPLAYCONFIG_MODE_INFO modes[256];
uint32_t modeCount = sizeof(modes) / sizeof(modes[0]);
static CALLBACK WINBOOL enumMonitorProc(HMONITOR hMonitor, FF_MAYBE_UNUSED HDC hDC, FF_MAYBE_UNUSED LPRECT rc, LPARAM lparam)
{
MONITORINFOEXW mi = { .cbSize = sizeof(mi) };
DataBundle* data = (DataBundle*) lparam;
if(GetMonitorInfoW(hMonitor, (MONITORINFO *)&mi) && wcscmp(mi.szDevice, data->deviceName) == 0)
if (QueryDisplayConfig(
QDC_ONLY_ACTIVE_PATHS,
&pathCount,
paths,
&modeCount,
modes,
NULL) == ERROR_SUCCESS)
{
data->width = (uint32_t) mi.rcMonitor.right;
data->height = (uint32_t) mi.rcMonitor.bottom;
return FALSE;
for (uint32_t i = 0; i < pathCount; ++i)
{
DISPLAYCONFIG_PATH_INFO* path = &paths[i];
DISPLAYCONFIG_SOURCE_DEVICE_NAME sourceName = {
.header = {
.type = DISPLAYCONFIG_DEVICE_INFO_GET_SOURCE_NAME,
.size = sizeof(sourceName),
.adapterId = path->sourceInfo.adapterId,
.id = path->sourceInfo.id,
},
};
uint32_t scaledWidth = 0, scaledHeight = 0;
if (DisplayConfigGetDeviceInfo(&sourceName.header) == ERROR_SUCCESS)
{
HDC hdc = CreateICW(sourceName.viewGdiDeviceName, NULL, NULL, NULL);
scaledWidth = (uint32_t) GetDeviceCaps(hdc, HORZRES);
scaledHeight = (uint32_t) GetDeviceCaps(hdc, VERTRES);
DeleteDC(hdc);
}
FF_STRBUF_AUTO_DESTROY name;
ffStrbufInit(&name);
if (detectName)
{
DISPLAYCONFIG_TARGET_DEVICE_NAME targetName = {
.header = {
.type = DISPLAYCONFIG_DEVICE_INFO_GET_TARGET_NAME,
.size = sizeof(targetName),
.adapterId = path->targetInfo.adapterId,
.id = path->targetInfo.id,
},
};
if(DisplayConfigGetDeviceInfo(&targetName.header) == ERROR_SUCCESS)
{
if (targetName.flags.friendlyNameFromEdid)
ffStrbufSetWS(&name, targetName.monitorFriendlyDeviceName);
else
{
ffStrbufSetWS(&name, targetName.monitorDevicePath);
ffStrbufSubstrAfterFirstC(&name, '#');
ffStrbufSubstrBeforeFirstC(&name, '#');
}
}
}
uint32_t width = modes[path->sourceInfo.modeInfoIdx].sourceMode.width;
uint32_t height = modes[path->sourceInfo.modeInfoIdx].sourceMode.height;
if (path->targetInfo.rotation == DISPLAYCONFIG_ROTATION_ROTATE90 ||
path->targetInfo.rotation == DISPLAYCONFIG_ROTATION_ROTATE270)
{
uint32_t temp = width;
width = height;
height = temp;
}
ffdsAppendDisplay(ds,
width,
height,
path->targetInfo.refreshRate.Numerator / (double) path->targetInfo.refreshRate.Denominator,
scaledWidth,
scaledHeight,
&name,
path->targetInfo.outputTechnology == DISPLAYCONFIG_OUTPUT_TECHNOLOGY_INTERNAL ||
path->targetInfo.outputTechnology == DISPLAYCONFIG_OUTPUT_TECHNOLOGY_DISPLAYPORT_EMBEDDED ||
path->targetInfo.outputTechnology == DISPLAYCONFIG_OUTPUT_TECHNOLOGY_UDI_EMBEDDED
? FF_DISPLAY_TYPE_BUILTIN : FF_DISPLAY_TYPE_EXTERNAL
);
}
}
return TRUE;
}
void ffConnectDisplayServerImpl(FFDisplayServerResult* ds, const FFinstance* instance)
{
FF_UNUSED(instance);
BOOL enabled;
if(SUCCEEDED(DwmIsCompositionEnabled(&enabled)) && enabled == TRUE)
{
@@ -45,23 +113,7 @@ void ffConnectDisplayServerImpl(FFDisplayServerResult* ds, const FFinstance* ins
ffStrbufInit(&ds->deVersion);
ffListInit(&ds->displays, sizeof(FFDisplayResult));
DISPLAY_DEVICEW displayDevice = { .cb = sizeof(DISPLAY_DEVICEW) };
for(DWORD devNum = 0; EnumDisplayDevicesW(NULL, devNum, &displayDevice, 0) != 0; ++devNum)
{
if(!(displayDevice.StateFlags & DISPLAY_DEVICE_ACTIVE))
continue;
DEVMODEW devMode = { .dmSize = sizeof(DEVMODEW) };
if(EnumDisplaySettingsW(displayDevice.DeviceName, ENUM_CURRENT_SETTINGS, &devMode) == 0)
continue;
DataBundle data = {
.deviceName = displayDevice.DeviceName,
.width = 0,
.height = 0,
};
EnumDisplayMonitors(NULL, NULL, enumMonitorProc, (LPARAM)&data);
ffdsAppendDisplay(ds, devMode.dmPelsWidth, devMode.dmPelsHeight, devMode.dmDisplayFrequency, data.width, data.height);
}
detectDisplays(ds, instance->config.displayDetectName);
//https://github.com/hykilpikonna/hyfetch/blob/master/neofetch#L2067
const FFOSResult* os = ffDetectOS(instance);
@@ -74,7 +126,7 @@ void ffConnectDisplayServerImpl(FFDisplayServerResult* ds, const FFinstance* ins
) ffStrbufSetS(&ds->dePrettyName, "Fluent");
else if(
ffStrbufEqualS(&os->version, "8") ||
ffStrbufEqualS(&os->version, "81.") ||
ffStrbufEqualS(&os->version, "8.1") ||
ffStrbufEqualS(&os->version, "2012 R2") ||
ffStrbufEqualS(&os->version, "2012")
) ffStrbufSetS(&ds->dePrettyName, "Metro");
+81 -25
View File
@@ -9,6 +9,7 @@
#include "common/thread.h"
#include <wayland-client.h>
#include <sys/socket.h>
#include <assert.h>
typedef struct WaylandData
{
@@ -19,6 +20,7 @@ typedef struct WaylandData
FF_LIBRARY_SYMBOL(wl_display_roundtrip)
struct wl_display* display;
const struct wl_interface* ffwl_output_interface;
bool detectName;
} WaylandData;
typedef struct WaylandDisplay
@@ -27,6 +29,10 @@ typedef struct WaylandDisplay
int32_t height;
int32_t refreshRate;
int32_t scale;
enum wl_output_transform transform;
FFDisplayType type;
FFstrbuf name;
bool detectName;
} WaylandDisplay;
#ifndef __FreeBSD__
@@ -57,10 +63,8 @@ static void stubListener(void* data, ...)
(void) data;
}
static void waylandOutputModeListener(void* data, struct wl_output* output, uint32_t flags, int32_t width, int32_t height, int32_t refreshRate)
static void waylandOutputModeListener(void* data, FF_MAYBE_UNUSED struct wl_output* output, uint32_t flags, int32_t width, int32_t height, int32_t refreshRate)
{
FF_UNUSED(output);
if(!(flags & WL_OUTPUT_MODE_CURRENT))
return;
@@ -70,15 +74,46 @@ static void waylandOutputModeListener(void* data, struct wl_output* output, uint
display->refreshRate = refreshRate;
}
#if WAYLAND_VERSION_MINOR >= 2
static void waylandOutputScaleListener(void* data, struct wl_output* output, int32_t scale)
static void waylandOutputScaleListener(void* data, FF_MAYBE_UNUSED struct wl_output* output, int32_t scale)
{
FF_UNUSED(output);
WaylandDisplay* display = data;
display->scale = scale;
}
#endif
static void waylandOutputGeometryListener(void *data,
FF_MAYBE_UNUSED struct wl_output *output,
FF_MAYBE_UNUSED int32_t x,
FF_MAYBE_UNUSED int32_t y,
FF_MAYBE_UNUSED int32_t physical_width,
FF_MAYBE_UNUSED int32_t physical_height,
FF_MAYBE_UNUSED int32_t subpixel,
const char *make,
const char *model,
int32_t transform)
{
WaylandDisplay* display = data;
display->transform = (enum wl_output_transform) transform;
if(display->detectName)
{
if(make && strcmp(make, "unknown") != 0)
ffStrbufAppendS(&display->name, make);
if(model && strcmp(model, "unknown") != 0)
{
if(display->name.length > 0)
ffStrbufAppendC(&display->name, '-');
ffStrbufAppendS(&display->name, model);
}
}
}
static void waylandOutputNameListener(void *data, FF_MAYBE_UNUSED struct wl_output *output, const char *name)
{
WaylandDisplay* display = data;
if(strncmp(name, "eDP-", strlen("eDP-")) == 0)
display->type = FF_DISPLAY_TYPE_BUILTIN;
else if(strncmp(name, "HDMI-", strlen("HDMI-")) == 0 || strncmp(name, "DP-", strlen("DP-")) == 0)
display->type = FF_DISPLAY_TYPE_EXTERNAL;
}
static void waylandOutputHandler(WaylandData* wldata, struct wl_registry* registry, uint32_t name, uint32_t version)
{
@@ -87,28 +122,30 @@ static void waylandOutputHandler(WaylandData* wldata, struct wl_registry* regist
return;
WaylandDisplay display = {
.detectName = wldata->detectName,
.width = 0,
.height = 0,
.refreshRate = 0,
.scale = 1,
.transform = WL_OUTPUT_TRANSFORM_NORMAL,
.type = FF_DISPLAY_TYPE_UNKNOWN,
};
ffStrbufInit(&display.name);
struct wl_output_listener outputListener = {
.mode = waylandOutputModeListener,
.geometry = (void*) stubListener,
//https://lists.freedesktop.org/archives/wayland-devel/2013-July/010278.html
#if WAYLAND_VERSION_MINOR >= 2
.done = (void*) stubListener,
.scale = waylandOutputScaleListener,
#endif
//https://lists.freedesktop.org/archives/wayland-devel/2021-December/042064.html
#if WAYLAND_VERSION_MINOR >= 20
.name = (void*) stubListener,
.description = (void*) stubListener,
#endif
// Dirty hack for #477
// The order of these callbacks MUST follow `struct wl_output_listener`
void* outputListener[] = {
waylandOutputGeometryListener, // geometry
waylandOutputModeListener, // mode
stubListener, // done
waylandOutputScaleListener, // scale
waylandOutputNameListener, // name
stubListener, // description
};
static_assert(
sizeof(outputListener) >= sizeof(struct wl_output_listener),
"sizeof(outputListener) is too small. Please report it to fastfetch github issue"
);
wldata->ffwl_proxy_add_listener(output, (void(**)(void)) &outputListener, &display);
wldata->ffwl_display_roundtrip(wldata->display);
@@ -120,12 +157,29 @@ static void waylandOutputHandler(WaylandData* wldata, struct wl_registry* regist
static FFThreadMutex mutex = FF_THREAD_MUTEX_INITIALIZER;
ffThreadMutexLock(&mutex);
switch(display.transform)
{
case WL_OUTPUT_TRANSFORM_90:
case WL_OUTPUT_TRANSFORM_270:
case WL_OUTPUT_TRANSFORM_FLIPPED_90:
case WL_OUTPUT_TRANSFORM_FLIPPED_270: {
int32_t temp = display.width;
display.width = display.height;
display.height = temp;
break;
}
default:
break;
}
ffdsAppendDisplay(wldata->result,
(uint32_t) display.width,
(uint32_t) display.height,
ffdsParseRefreshRate(display.refreshRate / 1000),
display.refreshRate / 1000.0,
(uint32_t) (display.width / display.scale),
(uint32_t) (display.height / display.scale)
(uint32_t) (display.height / display.scale),
&display.name,
display.type
);
ffThreadMutexUnlock(&mutex);
@@ -162,6 +216,8 @@ bool detectWayland(const FFinstance* instance, FFDisplayServerResult* result)
if(data.display == NULL)
return false;
data.detectName = instance->config.displayDetectName;
waylandDetectWM(ffwl_display_get_fd(data.display), result);
struct wl_proxy* registry = ffwl_proxy_marshal_constructor((struct wl_proxy*) data.display, WL_DISPLAY_GET_REGISTRY, ffwl_registry_interface, NULL);
+32 -1
View File
@@ -125,14 +125,35 @@ static void getKDE(const FFinstance* instance, FFDisplayServerResult* result)
ffStrbufSetS(&result->deProcessName, "plasmashell");
ffStrbufSetS(&result->dePrettyName, FF_DE_PRETTY_PLASMA);
ffParsePropFileData(instance, "xsessions/plasma.desktop", "X-KDE-PluginInfo-Version =", &result->deVersion);
ffParsePropFileValues("/usr/share/xsessions/plasmax11.desktop", 1, (FFpropquery[]) {
{"X-KDE-PluginInfo-Version =", &result->deVersion}
});
if(result->deVersion.length == 0)
ffParsePropFileData(instance, "xsessions/plasma.desktop", "X-KDE-PluginInfo-Version =", &result->deVersion);
if(result->deVersion.length == 0)
ffParsePropFileData(instance, "xsessions/plasma5.desktop", "X-KDE-PluginInfo-Version =", &result->deVersion);
if(result->deVersion.length == 0)
{
ffParsePropFileValues("/usr/share/wayland-sessions/plasma.desktop", 1, (FFpropquery[]) {
{"X-KDE-PluginInfo-Version =", &result->deVersion}
});
}
if(result->deVersion.length == 0)
ffParsePropFileData(instance, "wayland-sessions/plasmawayland.desktop", "X-KDE-PluginInfo-Version =", &result->deVersion);
if(result->deVersion.length == 0)
ffParsePropFileData(instance, "wayland-sessions/plasmawayland5.desktop", "X-KDE-PluginInfo-Version =", &result->deVersion);
if(result->deVersion.length == 0 && instance->config.allowSlowOperations)
{
if (ffProcessAppendStdOut(&result->deVersion, (char* const[]){
"plasmashell",
"--version",
NULL
}) == NULL) // plasmashell 5.27.5
ffStrbufSubstrAfterLastC(&result->deVersion, ' ');
}
applyBetterWM(result, getenv("KDEWM"));
}
@@ -141,6 +162,16 @@ static void getGnome(const FFinstance* instance, FFDisplayServerResult* result)
ffStrbufSetS(&result->deProcessName, "gnome-shell");
ffStrbufSetS(&result->dePrettyName, FF_DE_PRETTY_GNOME);
ffParsePropFileData(instance, "gnome-shell/org.gnome.Extensions", "version :", &result->deVersion);
if (result->deVersion.length == 0)
{
if (ffProcessAppendStdOut(&result->deVersion, (char* const[]){
"gnome-shell",
"--version",
NULL
}) == NULL) // GNOME Shell 44.1
ffStrbufSubstrAfterLastC(&result->deVersion, ' ');
}
}
static void getCinnamon(const FFinstance* instance, FFDisplayServerResult* result)
+17 -10
View File
@@ -112,13 +112,14 @@ void ffdsConnectXcb(const FFinstance* instance, FFDisplayServerResult* result)
while(iterator.rem > 0)
{
ffdsAppendDisplay(
result,
ffdsAppendDisplay(result,
(uint32_t) iterator.data->width_in_pixels,
(uint32_t) iterator.data->height_in_pixels,
0,
(uint32_t) iterator.data->width_in_pixels,
(uint32_t) iterator.data->height_in_pixels
(uint32_t) iterator.data->height_in_pixels,
NULL,
FF_DISPLAY_TYPE_UNKNOWN
);
ffxcb_screen_next(&iterator);
}
@@ -174,9 +175,7 @@ typedef struct XcbRandrData
static bool xcbRandrHandleModeInfo(XcbRandrData* data, xcb_randr_mode_info_t* modeInfo)
{
uint32_t refreshRate = ffdsParseRefreshRate((int32_t) (
modeInfo->dot_clock / (uint32_t) (modeInfo->htotal * modeInfo->vtotal)
));
double refreshRate = (double) modeInfo->dot_clock / (double) (modeInfo->htotal * modeInfo->vtotal);
return ffdsAppendDisplay(
data->result,
@@ -184,7 +183,9 @@ static bool xcbRandrHandleModeInfo(XcbRandrData* data, xcb_randr_mode_info_t* mo
(uint32_t) modeInfo->height,
refreshRate == 0 ? data->defaultRefreshRate : refreshRate,
(uint32_t) modeInfo->width,
(uint32_t) modeInfo->height
(uint32_t) modeInfo->height,
NULL,
FF_DISPLAY_TYPE_UNKNOWN
);
}
@@ -221,7 +222,9 @@ static bool xcbRandrHandleCrtc(XcbRandrData* data, xcb_randr_crtc_t crtc)
(uint32_t) crtcInfoReply->height,
data->defaultRefreshRate,
(uint32_t) crtcInfoReply->width,
(uint32_t) crtcInfoReply->height
(uint32_t) crtcInfoReply->height,
NULL,
FF_DISPLAY_TYPE_UNKNOWN
);
free(crtcInfoReply);
@@ -266,7 +269,9 @@ static bool xcbRandrHandleMonitor(XcbRandrData* data, xcb_randr_monitor_info_t*
(uint32_t) monitor->height,
data->defaultRefreshRate,
(uint32_t) monitor->width,
(uint32_t) monitor->height
(uint32_t) monitor->height,
NULL,
FF_DISPLAY_TYPE_UNKNOWN
);
}
@@ -326,7 +331,9 @@ static void xcbRandrHandleScreen(XcbRandrData* data, xcb_screen_t* screen)
(uint32_t) screen->height_in_pixels,
data->defaultRefreshRate,
(uint32_t) screen->width_in_pixels,
(uint32_t) screen->height_in_pixels
(uint32_t) screen->height_in_pixels,
NULL,
FF_DISPLAY_TYPE_UNKNOWN
);
}
+17 -10
View File
@@ -77,13 +77,14 @@ void ffdsConnectXlib(const FFinstance* instance, FFDisplayServerResult* result)
for(int i = 0; i < ScreenCount(display); i++)
{
Screen* screen = ScreenOfDisplay(display, i);
ffdsAppendDisplay(
result,
ffdsAppendDisplay(result,
(uint32_t) WidthOfScreen(screen),
(uint32_t) HeightOfScreen(screen),
0,
(uint32_t) WidthOfScreen(screen),
(uint32_t) HeightOfScreen(screen)
(uint32_t) HeightOfScreen(screen),
NULL,
FF_DISPLAY_TYPE_UNKNOWN
);
}
@@ -133,9 +134,7 @@ typedef struct XrandrData
static bool xrandrHandleModeInfo(XrandrData* data, XRRModeInfo* modeInfo)
{
uint32_t refreshRate = ffdsParseRefreshRate((int32_t) (
modeInfo->dotClock / (modeInfo->hTotal * modeInfo->vTotal)
));
double refreshRate = (double) modeInfo->dotClock / (double) (modeInfo->hTotal * modeInfo->vTotal);
return ffdsAppendDisplay(
data->result,
@@ -143,7 +142,9 @@ static bool xrandrHandleModeInfo(XrandrData* data, XRRModeInfo* modeInfo)
(uint32_t) modeInfo->height,
refreshRate == 0 ? data->defaultRefreshRate : refreshRate,
(uint32_t) modeInfo->width,
(uint32_t) modeInfo->height
(uint32_t) modeInfo->height,
NULL,
FF_DISPLAY_TYPE_UNKNOWN
);
}
@@ -174,7 +175,9 @@ static bool xrandrHandleCrtc(XrandrData* data, RRCrtc crtc)
(uint32_t) crtcInfo->height,
data->defaultRefreshRate,
(uint32_t) crtcInfo->width,
(uint32_t) crtcInfo->height
(uint32_t) crtcInfo->height,
NULL,
FF_DISPLAY_TYPE_UNKNOWN
);
data->ffXRRFreeCrtcInfo(crtcInfo);
@@ -210,7 +213,9 @@ static bool xrandrHandleMonitor(XrandrData* data, XRRMonitorInfo* monitorInfo)
(uint32_t) monitorInfo->height,
data->defaultRefreshRate,
(uint32_t) monitorInfo->width,
(uint32_t) monitorInfo->height
(uint32_t) monitorInfo->height,
NULL,
FF_DISPLAY_TYPE_UNKNOWN
);
}
@@ -264,7 +269,9 @@ static void xrandrHandleScreen(XrandrData* data, Screen* screen)
(uint32_t) HeightOfScreen(screen),
data->defaultRefreshRate,
(uint32_t) WidthOfScreen(screen),
(uint32_t) HeightOfScreen(screen)
(uint32_t) HeightOfScreen(screen),
NULL,
FF_DISPLAY_TYPE_UNKNOWN
);
}
+1
View File
@@ -9,6 +9,7 @@ static void detectFont(const FFinstance* instance, FFFontResult* font)
for(uint32_t i = 0; i < FF_DETECT_FONT_NUM_FONTS; ++i)
ffStrbufInit(&font->fonts[i]);
ffStrbufInit(&font->display);
ffDetectFontImpl(instance, font);
+1
View File
@@ -18,6 +18,7 @@ typedef struct FFFontResult
* Other: Unset, Unset, Unset, Unset
*/
FFstrbuf fonts[FF_DETECT_FONT_NUM_FONTS];
FFstrbuf display;
} FFFontResult;
const FFFontResult* ffDetectFont(const FFinstance* instance);
+18
View File
@@ -4,6 +4,23 @@
#import <AppKit/NSFont.h>
static void generateString(FFFontResult* font)
{
if(font->fonts[0].length > 0)
{
ffStrbufAppend(&font->display, &font->fonts[0]);
ffStrbufAppendS(&font->display, " [System]");
if(font->fonts[1].length > 0)
ffStrbufAppendS(&font->display, ", ");
}
if(font->fonts[1].length > 0)
{
ffStrbufAppend(&font->display, &font->fonts[1]);
ffStrbufAppendS(&font->display, " [User]");
}
}
void ffDetectFontImpl(const FFinstance* instance, FFFontResult* result)
{
FF_UNUSED(instance);
@@ -11,4 +28,5 @@ void ffDetectFontImpl(const FFinstance* instance, FFFontResult* result)
ffStrbufAppendS(&result->fonts[1], [NSFont userFontOfSize:12].familyName.UTF8String);
ffStrbufAppendS(&result->fonts[2], [NSFont monospacedSystemFontOfSize:12 weight:400].familyName.UTF8String);
ffStrbufAppendS(&result->fonts[3], [NSFont userFixedPitchFontOfSize:12].familyName.UTF8String);
generateString(result);
}
+32
View File
@@ -1,9 +1,39 @@
#include "common/font.h"
#include "common/parsing.h"
#include "detection/displayserver/displayserver.h"
#include "detection/gtk_qt/gtk_qt.h"
#include "font.h"
static void generateString(FFFontResult* font)
{
if(font->fonts[0].length > 0)
{
ffStrbufAppend(&font->display, &font->fonts[0]);
ffStrbufAppendS(&font->display, " [QT]");
for(uint8_t i = 1; i < sizeof(font->fonts) / sizeof(font->fonts[0]); i++)
{
if(font->fonts[i].length > 0)
{
ffStrbufAppendS(&font->display, ", ");
break;
}
}
}
ffParseGTK(&font->display, &font->fonts[1], &font->fonts[2], &font->fonts[3]);
}
void ffDetectFontImpl(const FFinstance* instance, FFFontResult* result)
{
const FFDisplayServerResult* wmde = ffConnectDisplayServer(instance);
if(ffStrbufIgnCaseCompS(&wmde->wmProtocolName, FF_WM_PROTOCOL_TTY) == 0)
{
ffStrbufAppendS(&result->error, "Font isn't supported in TTY");
return;
}
FFfont qt;
ffFontInitQt(&qt, ffDetectQt(instance)->font.chars);
ffStrbufAppend(&result->fonts[0], &qt.pretty);
@@ -23,4 +53,6 @@ void ffDetectFontImpl(const FFinstance* instance, FFFontResult* result)
ffFontInitPango(&gtk4, ffDetectGTK4(instance)->font.chars);
ffStrbufAppend(&result->fonts[3], &gtk4.pretty);
ffFontDestroy(&gtk4);
generateString(result);
}
+23 -1
View File
@@ -1,7 +1,27 @@
#include "font.h"
#include "util/windows/unicode.h"
#include <winuser.h>
#include <windows.h>
static void generateString(FFFontResult* font)
{
const char* types[] = { "Caption", "Menu", "Message", "Status" };
for(uint32_t i = 0; i < sizeof(types) / sizeof(types[0]); ++i)
{
if(i == 0 || !ffStrbufEqual(&font->fonts[i - 1], &font->fonts[i]))
{
if(i > 0)
ffStrbufAppendS(&font->display, "], ");
ffStrbufAppendF(&font->display, "%s [%s", font->fonts[i].chars, types[i]);
}
else
{
ffStrbufAppendS(&font->display, " / ");
ffStrbufAppendS(&font->display, types[i]);
}
}
ffStrbufAppendC(&font->display, ']');
}
void ffDetectFontImpl(const FFinstance* instance, FFFontResult* result)
{
@@ -19,4 +39,6 @@ void ffDetectFontImpl(const FFinstance* instance, FFFontResult* result)
if(fonts[i]->lfHeight < 0)
ffStrbufAppendF(&result->fonts[i], " (%dpt)", (int)-fonts[i]->lfHeight);
}
generateString(result);
}
+138
View File
@@ -0,0 +1,138 @@
#include "gamepad.h"
#include "common/io/io.h"
#include "util/mallocHelper.h"
#include "util/windows/unicode.h"
#include <windows.h>
#include <hidsdi.h>
static const char* detectKnownGamepad(uint32_t vendorId, uint32_t productId)
{
switch (vendorId)
{
// Nintendo
case 0x057E:
{
switch (productId)
{
case 0x2006: return "Nintendo Switch Joycon L";
case 0x2007: return "Nintendo Switch Joycon R";
case 0x2009: return "Nintendo Switch Pro Controller";
case 0x200E: return "Nintendo Switch Charging Grip";
case 0x2017: return "Nintendo Switch SNES Controller";
default: return NULL;
}
}
// Sony
case 0x054C:
{
switch (productId)
{
case 0x0268: return "Sony Playstation 3 Controller";
case 0x05C4: return "Sony DualShock 4 Gen1";
case 0x09CC: return "Sony DualShock 4 Gen2";
case 0x0BA0: return "Sony PS4 Controller USB receiver";
case 0x0CE6: return "Sony DualSense";
default: return NULL;
}
}
// Microsoft
case 0x045E:
{
switch (productId)
{
case 0x02E0: return "Microsoft X-Box One S pad (Wireless)";
case 0x02FD: return "Microsoft X-Box One S pad (Wireless, 2016 FW)";
case 0x0B05: return "Microsoft X-Box One Elite Series 2 pad (Wireless)";
case 0x0B13: return "Microsoft X-Box Series X (Wireless)";
case 0x028E: return "Microsoft XBox 360";
case 0x028F: return "Microsoft XBox 360 v2";
case 0x02A1: return "Microsoft XBox 360";
case 0x0291: return "Microsoft XBox 360 USB receiver";
case 0x02A0: return "Microsoft XBox 360 Big Button IR";
case 0x02DD: return "Microsoft XBox One";
case 0xB326: return "Microsoft XBox One Firmware 2015";
case 0x02E3: return "Microsoft XBox One Elite";
case 0x02FF: return "Microsoft XBox One Elite";
case 0x02EA: return "Microsoft XBox One S";
default: return NULL;
}
}
// Logitech
case 0x046D:
{
switch (productId)
{
case 0xC216: return "Logitech F310, DirectInput";
case 0xC218: return "Logitech F510, DirectInput";
case 0xC219: return "Logitech F710, DirectInput";
case 0xC21D: return "Logitech F310";
case 0xC21E: return "Logitech F510";
case 0xC21F: return "Logitech F710";
default: return NULL;
}
}
default: return NULL;
}
}
const char* ffDetectGamepad(FF_MAYBE_UNUSED const FFinstance* instance, FFlist* devices /* List of FFGamepadDevice */)
{
UINT nDevices = 0;
if (GetRawInputDeviceList(NULL, &nDevices, sizeof(RAWINPUTDEVICELIST)))
return "GetRawInputDeviceList(NULL) failed";
if (nDevices == 0)
return "No HID devices found";
RAWINPUTDEVICELIST* FF_AUTO_FREE pRawInputDeviceList = (RAWINPUTDEVICELIST*) malloc(sizeof(RAWINPUTDEVICELIST) * nDevices);
if ((nDevices = GetRawInputDeviceList(pRawInputDeviceList, &nDevices, sizeof(RAWINPUTDEVICELIST))) == (UINT) -1)
return "GetRawInputDeviceList(pRawInputDeviceList) failed";
for (UINT i = 0; i < nDevices; ++i) {
if (pRawInputDeviceList[i].dwType != 2) continue;
HANDLE hDevice = pRawInputDeviceList[i].hDevice;
RID_DEVICE_INFO rdi;
UINT rdiSize = sizeof(rdi);
if (GetRawInputDeviceInfoW(hDevice, RIDI_DEVICEINFO, &rdi, &rdiSize) == (UINT) -1)
continue;
if (rdi.hid.usUsagePage != 1 || rdi.hid.usUsage != 5) // Gamepad
continue;
WCHAR devName[MAX_PATH] = L"";
UINT nameSize = MAX_PATH;
if (GetRawInputDeviceInfoW(hDevice, RIDI_DEVICENAME, devName, &nameSize) == (UINT) -1)
continue;
FFGamepadDevice* device = (FFGamepadDevice*) ffListAdd(devices);
ffStrbufInitWS(&device->identifier, devName);
ffStrbufInit(&device->name);
const char* knownGamepad = detectKnownGamepad(rdi.hid.dwVendorId, rdi.hid.dwProductId);
if (knownGamepad)
ffStrbufSetS(&device->name, knownGamepad);
else
{
wchar_t displayName[126];
HANDLE FF_AUTO_CLOSE_FD hHidFile = CreateFileW(devName, GENERIC_READ | GENERIC_WRITE, FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, OPEN_EXISTING, 0, NULL);
if (hHidFile && HidD_GetProductString(hHidFile, displayName, sizeof(wchar_t) * 126))
ffStrbufSetWS(&device->name, displayName);
else
ffStrbufSetF(&device->name, "Unknown gamepad %4X-%4X", rdi.hid.dwVendorId, rdi.hid.dwProductId);
}
}
return NULL;
}
-32
View File
@@ -1,32 +0,0 @@
extern "C" {
#include "gamepad.h"
}
#include <initguid.h>
#define DIRECTINPUT_VERSION 0x0800
#include <dinput.h>
CALLBACK BOOL DIEnumDevicesCallback(LPCDIDEVICEINSTANCEA lpddi, LPVOID pvRef)
{
FFlist* devices = (FFlist*) pvRef;
FFGamepadDevice* device = (FFGamepadDevice*) ffListAdd(devices);
ffStrbufInitF(&device->identifier, "{%08lX-%04hX-%04hX-%02hhX%02hhX-%02hhX%02hhX%02hhX%02hhX%02hhX%02hhX}",
lpddi->guidInstance.Data1, lpddi->guidInstance.Data2, lpddi->guidInstance.Data3,
lpddi->guidInstance.Data4[0], lpddi->guidInstance.Data4[1], lpddi->guidInstance.Data4[2], lpddi->guidInstance.Data4[3],
lpddi->guidInstance.Data4[4], lpddi->guidInstance.Data4[5], lpddi->guidInstance.Data4[6], lpddi->guidInstance.Data4[7]);
ffStrbufInitS(&device->name, lpddi->tszInstanceName);
return DIENUM_CONTINUE;
}
extern "C"
const char* ffDetectGamepad(FF_MAYBE_UNUSED const FFinstance* instance, FFlist* devices /* List of FFGamepadDevice */)
{
IDirectInput8A* dinput;
if (!SUCCEEDED(DirectInput8Create(GetModuleHandleW(NULL), DIRECTINPUT_VERSION, IID_IDirectInput8A, (void**)&dinput, NULL)))
return "DirectInput8Create() failed";
dinput->EnumDevices(DI8DEVCLASS_GAMECTRL, DIEnumDevicesCallback, devices, DIEDFL_ATTACHEDONLY);
dinput->Release();
return NULL;
}
+1 -1
View File
@@ -36,7 +36,7 @@ const FFlist* ffDetectGPU(const FFinstance* instance)
{
FF_DETECTION_INTERNAL_GUARD(FFlist,
ffListInit(&result, sizeof(FFGPUResult));
if(ffDetectGPUImpl(&result, instance) != NULL)
if(instance->config.gpuForceVulkan || ffDetectGPUImpl(&result, instance) != NULL)
{
const FFVulkanResult* vulkan = ffDetectVulkan(instance);
result = vulkan->gpus;
+1 -1
View File
@@ -29,7 +29,6 @@ typedef struct FFGPUMemory
typedef struct FFGPUResult
{
uint64_t id;
FFGpuType type;
FFstrbuf vendor;
FFstrbuf name;
@@ -38,6 +37,7 @@ typedef struct FFGPUResult
int coreCount;
FFGPUMemory dedicated;
FFGPUMemory shared;
uint32_t vulkanDeviceId; // Only used for vulkan
} FFGPUResult;
const FFlist* ffDetectGPU(const FFinstance* instance);
+20 -18
View File
@@ -5,7 +5,6 @@
#include "util/apple/cf_helpers.h"
#include <IOKit/graphics/IOGraphicsLib.h>
#include <wchar.h>
static double detectGpuTemp(const FFstrbuf* gpuName)
{
@@ -60,27 +59,21 @@ const char* ffDetectGPUImpl(FFlist* gpus, const FFinstance* instance)
FFGPUResult* gpu = ffListAdd(gpus);
gpu->id = 0;
gpu->dedicated.total = gpu->dedicated.used = gpu->shared.total = gpu->shared.used = FF_GPU_VMEM_SIZE_UNSET;
gpu->type = FF_GPU_TYPE_UNKNOWN;
ffStrbufInit(&gpu->vendor);
int vendorId;
if(!ffCfDictGetInt(properties, CFSTR("vendor-id"), &vendorId))
{
const char* vendorStr = ffGetGPUVendorString((unsigned) vendorId);
ffStrbufAppendS(&gpu->vendor, vendorStr);
if (vendorStr == FF_GPU_VENDOR_NAME_APPLE || vendorStr == FF_GPU_VENDOR_NAME_INTEL)
gpu->type = FF_GPU_TYPE_INTEGRATED;
else if (vendorStr == FF_GPU_VENDOR_NAME_NVIDIA || vendorStr == FF_GPU_VENDOR_NAME_AMD)
gpu->type = FF_GPU_TYPE_DISCRETE;
}
ffStrbufInit(&gpu->driver);
ffStrbufInit(&gpu->driver); // Ok for both Apple and Intel
ffCfDictGetString(properties, CFSTR("CFBundleIdentifier"), &gpu->driver);
int vram; // Supported on Intel
if(!ffCfDictGetInt(properties, CFSTR("VRAM,totalMB"), &vram))
gpu->dedicated.total = (uint64_t) vram * 1024 * 1024;
if(ffCfDictGetInt(properties, CFSTR("gpu-core-count"), &gpu->coreCount)) // For Apple
gpu->coreCount = FF_GPU_CORE_COUNT_UNSET;
ffStrbufInit(&gpu->name);
//IOAccelerator returns model property for Apple Silicon, but not for Intel Iris GPUs.
//IOAccelerator returns model / vendor-id properties for Apple Silicon, but not for Intel Iris GPUs.
//Still needs testing for AMD's
if(ffCfDictGetString(properties, CFSTR("model"), &gpu->name))
{
@@ -97,8 +90,17 @@ const char* ffDetectGPUImpl(FFlist* gpus, const FFinstance* instance)
ffCfDictGetString(properties, CFSTR("model"), &gpu->name);
}
if(ffCfDictGetInt(properties, CFSTR("gpu-core-count"), &gpu->coreCount))
gpu->coreCount = FF_GPU_CORE_COUNT_UNSET;
ffStrbufInit(&gpu->vendor);
int vendorId;
if(!ffCfDictGetInt(properties, CFSTR("vendor-id"), &vendorId))
{
const char* vendorStr = ffGetGPUVendorString((unsigned) vendorId);
ffStrbufAppendS(&gpu->vendor, vendorStr);
if (vendorStr == FF_GPU_VENDOR_NAME_APPLE || vendorStr == FF_GPU_VENDOR_NAME_INTEL)
gpu->type = FF_GPU_TYPE_INTEGRATED;
else if (vendorStr == FF_GPU_VENDOR_NAME_NVIDIA || vendorStr == FF_GPU_VENDOR_NAME_AMD)
gpu->type = FF_GPU_TYPE_DISCRETE;
}
if(instance->config.gpuTemp)
gpu->temperature = detectGpuTemp(&gpu->name);
+38 -7
View File
@@ -10,6 +10,7 @@
#include <string.h>
#include <unistd.h>
#include <pci/pci.h>
#include <setjmp.h>
typedef struct PCIData
{
@@ -35,17 +36,17 @@ static void pciDetectVendorName(FFGPUResult* gpu, PCIData* pci, struct pci_dev*
pci->ffpci_lookup_name(pci->access, gpu->vendor.chars, (int) gpu->vendor.allocated, PCI_LOOKUP_VENDOR, device->vendor_id);
ffStrbufRecalculateLength(&gpu->vendor);
if(ffStrbufFirstIndexS(&gpu->vendor, "AMD") < gpu->vendor.length || ffStrbufFirstIndexS(&gpu->vendor, "ATI") < gpu->vendor.length)
if(ffStrbufContainS(&gpu->vendor, "AMD") || ffStrbufContainS(&gpu->vendor, "ATI"))
ffStrbufSetS(&gpu->vendor, FF_GPU_VENDOR_NAME_AMD);
else if(ffStrbufFirstIndexS(&gpu->vendor, "Intel") < gpu->vendor.length)
else if(ffStrbufContainS(&gpu->vendor, "Intel"))
ffStrbufSetS(&gpu->vendor, FF_GPU_VENDOR_NAME_INTEL);
else if(ffStrbufFirstIndexS(&gpu->vendor, "NVIDIA") < gpu->vendor.length)
else if(ffStrbufContainS(&gpu->vendor, "NVIDIA"))
ffStrbufSetS(&gpu->vendor, FF_GPU_VENDOR_NAME_NVIDIA);
}
static void drmDetectDeviceName(const FFinstance* instance, FFGPUResult* gpu, PCIData* pci, struct pci_dev* device)
{
u8 revId;
u8 revId = 0;
bool revIdSet = false;
#if PCI_LIB_VERSION >= 0x030800
@@ -199,8 +200,7 @@ static void pciHandleDevice(const FFinstance* instance, FFlist* results, PCIData
FFGPUResult* gpu = ffListAdd(results);
gpu->id = 0;
gpu->dedicated.total = gpu->dedicated.used = gpu->shared.total = gpu->shared.used = FF_GPU_VMEM_SIZE_UNSET;
gpu->dedicated.total = gpu->dedicated.used = gpu->shared.total = gpu->shared.used = FF_GPU_VMEM_SIZE_UNSET;
ffStrbufInit(&gpu->vendor);
pciDetectVendorName(gpu, pci, device);
@@ -220,6 +220,30 @@ static void pciHandleDevice(const FFinstance* instance, FFlist* results, PCIData
pciDetectTemperatur(gpu, device);
}
jmp_buf pciInitJmpBuf;
static void __attribute__((__noreturn__))
handlePciInitError(FF_MAYBE_UNUSED char *msg, ...)
{
longjmp(pciInitJmpBuf, 1);
}
// https://github.com/pciutils/pciutils/blob/bca0412843fa650c749128ade03f35ab3e8fe2b9/lib/init.c#L186
static void __attribute__((__noreturn__))
handlePciGenericError(char *msg, ...)
{
va_list args;
va_start(args, msg);
fputs("pcilib: ", stderr);
vfprintf(stderr, msg, args);
va_end(args);
fputc('\n', stderr);
exit(1);
}
static void handlePciWarning(FF_MAYBE_UNUSED char *msg, ...)
{
// noop
}
static const char* pciDetectGPUs(const FFinstance* instance, FFlist* gpus)
{
PCIData pci;
@@ -240,7 +264,14 @@ static const char* pciDetectGPUs(const FFinstance* instance, FFlist* gpus)
#endif
pci.access = ffpci_alloc();
ffpci_init(pci.access);
pci.access->warning = handlePciWarning;
pci.access->error = handlePciInitError;
if(setjmp(pciInitJmpBuf) == 0) // https://github.com/pciutils/pciutils/issues/136
ffpci_init(pci.access);
else
return "pcilib: Cannot find any working access method.";
pci.access->error = handlePciGenericError; // set back to generic error so we don't mess up error handling in other places
ffpci_scan_bus(pci.access);
struct pci_dev* device = pci.access->devices;
+71
View File
@@ -0,0 +1,71 @@
#include "gpu.h"
#include "util/windows/unicode.h"
#include "util/windows/registry.h"
#include <inttypes.h>
static int isGpuNameEqual(const FFGPUResult* gpu, const FFstrbuf* name)
{
return ffStrbufEqual(&gpu->name, name);
}
const char* ffDetectGPUImpl(FFlist* gpus, FF_MAYBE_UNUSED const FFinstance* instance)
{
DISPLAY_DEVICEW displayDevice = { .cb = sizeof(displayDevice) };
wchar_t regKey[MAX_PATH] = L"SYSTEM\\CurrentControlSet\\Control\\Video\\{";
const uint32_t regKeyPrefixLength = (uint32_t) wcslen(regKey);
const uint32_t deviceKeyPrefixLength = strlen("\\Registry\\Machine\\") + regKeyPrefixLength;
for (DWORD i = 0; EnumDisplayDevicesW(NULL, i, &displayDevice, 0); ++i)
{
if (displayDevice.StateFlags & DISPLAY_DEVICE_MIRRORING_DRIVER) continue;
const uint32_t deviceKeyLength = (uint32_t) wcslen(displayDevice.DeviceKey);
if (__builtin_expect(deviceKeyLength == 100, true))
{
if (wmemcmp(&displayDevice.DeviceKey[deviceKeyLength - 4], L"0000", 4) != 0) continue;
}
else
{
// DeviceKey can be empty. See #484
FF_STRBUF_AUTO_DESTROY gpuName = ffStrbufCreateWS(displayDevice.DeviceString);
if (ffListFirstIndexComp(gpus, &gpuName, (void*) isGpuNameEqual) != gpus->length) continue;
}
FFGPUResult* gpu = (FFGPUResult*)ffListAdd(gpus);
ffStrbufInit(&gpu->vendor);
ffStrbufInitWS(&gpu->name, displayDevice.DeviceString);
ffStrbufInit(&gpu->driver);
gpu->temperature = FF_GPU_TEMP_UNSET;
gpu->coreCount = FF_GPU_CORE_COUNT_UNSET;
gpu->type = FF_GPU_TYPE_UNKNOWN;
gpu->dedicated.total = gpu->dedicated.used = gpu->shared.total = gpu->shared.used = FF_GPU_VMEM_SIZE_UNSET;
if (deviceKeyLength == 100 && displayDevice.DeviceKey[deviceKeyPrefixLength - 1] == '{')
{
wmemcpy(regKey + regKeyPrefixLength, displayDevice.DeviceKey + deviceKeyPrefixLength, 100 - regKeyPrefixLength + 1);
FF_HKEY_AUTO_DESTROY hKey = NULL;
if (!ffRegOpenKeyForRead(HKEY_LOCAL_MACHINE, regKey, &hKey, NULL)) continue;
ffRegReadStrbuf(hKey, L"DriverVersion", &gpu->driver, NULL);
ffRegReadStrbuf(hKey, L"ProviderName", &gpu->vendor, NULL);
if(ffStrbufContainS(&gpu->vendor, "AMD") || ffStrbufContainS(&gpu->vendor, "ATI"))
ffStrbufSetS(&gpu->vendor, FF_GPU_VENDOR_NAME_AMD);
else if(ffStrbufContainS(&gpu->vendor, "Intel"))
ffStrbufSetS(&gpu->vendor, FF_GPU_VENDOR_NAME_INTEL);
else if(ffStrbufContainS(&gpu->vendor, "NVIDIA"))
ffStrbufSetS(&gpu->vendor, FF_GPU_VENDOR_NAME_NVIDIA);
if (!ffRegReadUint64(hKey, L"HardwareInformation.qwMemorySize", &gpu->dedicated.total, NULL))
{
uint32_t vmem = 0;
if (ffRegReadUint(hKey, L"HardwareInformation.MemorySize", &vmem, NULL))
gpu->dedicated.total = vmem;
}
gpu->type = gpu->dedicated.total > 1024 * 1024 * 1024 ? FF_GPU_TYPE_DISCRETE : FF_GPU_TYPE_INTEGRATED;
}
}
return NULL;
}
-172
View File
@@ -1,172 +0,0 @@
extern "C" {
#include "gpu.h"
#include "util/windows/unicode.h"
#include "util/windows/registry.h"
}
#include "util/windows/wmi.hpp"
#include <dxgi.h>
#include <wchar.h>
#include <inttypes.h>
static const char* detectWithRegistry(FFlist* gpus)
{
// Ref: https://github.com/lptstr/winfetch/pull/155
FF_HKEY_AUTO_DESTROY hKey = NULL;
if(!ffRegOpenKeyForRead(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Microsoft\\DirectX", &hKey, nullptr))
return "Open \"HKLM\\SOFTWARE\\Microsoft\\DirectX\" failed";
uint64_t lastSeen;
if(!ffRegReadUint64(hKey, L"LastSeen", &lastSeen, nullptr))
return "Read \"HKLM\\SOFTWARE\\Microsoft\\DirectX\\LastSeen\" failed";
DWORD index = 0;
wchar_t subKeyName[64];
while(true)
{
DWORD subKeySize = sizeof(subKeyName) / sizeof(*subKeyName);
if(RegEnumKeyExW(hKey, index++, subKeyName, &subKeySize, nullptr, nullptr, nullptr, nullptr) != ERROR_SUCCESS)
break;
FF_HKEY_AUTO_DESTROY hSubKey = NULL;
if(!ffRegOpenKeyForRead(hKey, subKeyName, &hSubKey, nullptr))
continue;
uint64_t adapterLastSeen;
if(!ffRegReadUint64(hSubKey, L"LastSeen", &adapterLastSeen, nullptr) || lastSeen != adapterLastSeen)
continue;
uint32_t softwareAdapter;
if(!ffRegReadUint(hSubKey, L"SoftwareAdapter", &softwareAdapter, nullptr) || softwareAdapter)
continue;
FFGPUResult* gpu = (FFGPUResult*)ffListAdd(gpus);
ffStrbufInit(&gpu->vendor);
ffStrbufInit(&gpu->name);
ffStrbufInit(&gpu->driver);
gpu->temperature = FF_GPU_TEMP_UNSET;
gpu->coreCount = FF_GPU_CORE_COUNT_UNSET;
gpu->type = FF_GPU_TYPE_UNKNOWN;
gpu->id = 0;
gpu->dedicated.total = gpu->dedicated.used = gpu->shared.total = gpu->shared.used = FF_GPU_VMEM_SIZE_UNSET;
ffRegReadUint64(hSubKey, L"AdapterLuid", &gpu->id, nullptr);
ffRegReadStrbuf(hSubKey, L"Description", &gpu->name, nullptr);
uint32_t vendorId;
if(ffRegReadUint(hSubKey, L"VendorId", &vendorId, nullptr))
ffStrbufAppendS(&gpu->vendor, ffGetGPUVendorString(vendorId));
uint64_t dedicatedVideoMemory = 0;
if(ffRegReadUint64(hSubKey, L"DedicatedVideoMemory", &dedicatedVideoMemory, nullptr))
gpu->type = dedicatedVideoMemory >= 1024 * 1024 * 1024 ? FF_GPU_TYPE_DISCRETE : FF_GPU_TYPE_INTEGRATED;
uint64_t dedicatedSystemMemory, sharedSystemMemory;
if(ffRegReadUint64(hSubKey, L"DedicatedSystemMemory", &dedicatedSystemMemory, nullptr) &&
ffRegReadUint64(hSubKey, L"SharedSystemMemory", &sharedSystemMemory, nullptr))
{
gpu->dedicated.total = dedicatedVideoMemory + dedicatedSystemMemory;
gpu->shared.total = sharedSystemMemory;
}
uint64_t driverVersion;
if(ffRegReadUint64(hSubKey, L"DriverVersion", &driverVersion, nullptr))
{
ffStrbufSetF(&gpu->driver, "%" PRIu64 ".%" PRIu64 ".%" PRIu64 ".%" PRIu64,
(driverVersion >> 48) & 0xFFFF,
(driverVersion >> 32) & 0xFFFF,
(driverVersion >> 16) & 0xFFFF,
(driverVersion >> 0) & 0xFFFF);
}
}
return nullptr;
}
static const char* detectWithDxgi(FFlist* gpus)
{
IDXGIFactory1* pFactory;
if(FAILED(CreateDXGIFactory1(__uuidof(IDXGIFactory1), (void**)(&pFactory))))
return "CreateDXGIFactory1() failed";
for(unsigned iAdapter = 0;; ++iAdapter)
{
IDXGIAdapter1* adapter;
if(FAILED(pFactory->EnumAdapters1(iAdapter, &adapter)))
break;
DXGI_ADAPTER_DESC1 desc;
if(FAILED(adapter->GetDesc1(&desc)) || (desc.Flags & DXGI_ADAPTER_FLAG_SOFTWARE))
continue;
FFGPUResult* gpu = (FFGPUResult*)ffListAdd(gpus);
gpu->dedicated.total = gpu->dedicated.total = gpu->shared.total = gpu->shared.used = FF_GPU_VMEM_SIZE_UNSET;
ffStrbufInit(&gpu->vendor);
ffStrbufAppendS(&gpu->vendor, ffGetGPUVendorString(desc.VendorId));
gpu->id = (uint64_t&)desc.AdapterLuid;
ffStrbufInit(&gpu->name);
ffStrbufSetWS(&gpu->name, desc.Description);
ffStrbufInit(&gpu->driver);
gpu->type = desc.DedicatedVideoMemory >= 1024 * 1024 * 1024 ? FF_GPU_TYPE_DISCRETE : FF_GPU_TYPE_INTEGRATED;
gpu->dedicated.total = desc.DedicatedVideoMemory + desc.DedicatedSystemMemory;
gpu->shared.total = desc.SharedSystemMemory;
adapter->Release();
gpu->temperature = FF_GPU_TEMP_UNSET;
gpu->coreCount = FF_GPU_CORE_COUNT_UNSET;
}
pFactory->Release();
return nullptr;
}
static const char* detectMemoryUsage(FFlist* gpus)
{
FFWmiQuery query(L"SELECT Name, DedicatedUsage, SharedUsage FROM Win32_PerfRawData_GPUPerformanceCounters_GPUAdapterMemory", nullptr);
if(!query)
return "Query WMI service failed";
FF_STRBUF_AUTO_DESTROY name;
ffStrbufInit(&name);
while(FFWmiRecord record = query.next())
{
record.getString(L"Name", &name); // luid_0x00000000_0x000146E8_phys_0
assert(name.length == strlen("luid_0x00000000_0x000146E8_phys_0"));
ffStrbufSubstrBefore(&name, strlen("luid_0x00000000_0x000146E8")); // luid_0x00000000_0x000146E8
ffStrbufSubstrAfter(&name, strlen("luid_0x00000000_0x") - 1); // 000146E8
uint64_t luid = strtoull(name.chars, nullptr, 16);
FF_LIST_FOR_EACH(FFGPUResult, gpu, *gpus)
{
if (gpu->id != luid) continue;
record.getUnsigned(L"DedicatedUsage", &gpu->dedicated.used);
record.getUnsigned(L"SharedUsage", &gpu->shared.used);
break;
}
}
return nullptr;
}
extern "C"
const char* ffDetectGPUImpl(FFlist* gpus, FF_MAYBE_UNUSED const FFinstance* instance)
{
const char* error = detectWithRegistry(gpus);
if (error)
error = detectWithDxgi(gpus);
if (!error && gpus->length > 0 && instance->config.allowSlowOperations)
detectMemoryUsage(gpus);
return error;
}
+14 -3
View File
@@ -13,7 +13,7 @@ static inline bool allPropertiesSet(FFGTKResult* result)
result->font.length > 0;
}
static inline void applyGTKSettings(FFGTKResult* result, const char* themeName, const char* iconsName, const char* fontName, const char* cursorTheme, int cursorSize)
static inline void applyGTKSettings(FFGTKResult* result, const char* themeName, const char* iconsName, const char* fontName, const char* cursorTheme, int cursorSize, const char* wallpaper)
{
if(result->theme.length == 0)
ffStrbufAppendS(&result->theme, themeName);
@@ -29,6 +29,9 @@ static inline void applyGTKSettings(FFGTKResult* result, const char* themeName,
if(result->cursorSize.length == 0 && cursorSize > 0)
ffStrbufAppendF(&result->cursorSize, "%i", cursorSize);
if(result->wallpaper.length == 0)
ffStrbufAppendS(&result->wallpaper, wallpaper);
}
static void detectGTKFromSettings(const FFinstance* instance, FFGTKResult* result)
@@ -40,6 +43,7 @@ static void detectGTKFromSettings(const FFinstance* instance, FFGTKResult* resul
static const char* fontName = NULL;
static const char* cursorTheme = NULL;
static int cursorSize = 0;
static const char* wallpaper = NULL;
static bool init = false;
@@ -48,7 +52,7 @@ static void detectGTKFromSettings(const FFinstance* instance, FFGTKResult* resul
if(init)
{
ffThreadMutexUnlock(&mutex);
applyGTKSettings(result, themeName, iconsName, fontName, cursorTheme, cursorSize);
applyGTKSettings(result, themeName, iconsName, fontName, cursorTheme, cursorSize, wallpaper);
return;
}
@@ -63,6 +67,9 @@ static void detectGTKFromSettings(const FFinstance* instance, FFGTKResult* resul
fontName = ffSettingsGetXFConf(instance, "xsettings", "/Gtk/FontName", FF_VARIANT_TYPE_STRING).strValue;
cursorTheme = ffSettingsGetXFConf(instance, "xsettings", "/Gtk/CursorThemeName", FF_VARIANT_TYPE_STRING).strValue;
cursorSize = ffSettingsGetXFConf(instance, "xsettings", "/Gtk/CursorThemeSize", FF_VARIANT_TYPE_INT).intValue;
wallpaper = ffSettingsGetXFConf(instance, "xfce4-desktop", "/backdrop/screen0/monitor0/workspace0/last-image", FF_VARIANT_TYPE_STRING).strValue;
if (!wallpaper) // FIXME: find a way to enumerate possible properties
wallpaper = ffSettingsGetXFConf(instance, "xfce4-desktop", "/backdrop/screen0/monitoreDP-1/workspace0/last-image", FF_VARIANT_TYPE_STRING).strValue;
}
else if(ffStrbufIgnCaseCompS(&wmde->dePrettyName, FF_DE_PRETTY_CINNAMON) == 0)
{
@@ -71,6 +78,7 @@ static void detectGTKFromSettings(const FFinstance* instance, FFGTKResult* resul
fontName = ffSettingsGet(instance, "/org/cinnamon/desktop/interface/font-name", "org.cinnamon.desktop.interface", NULL, "font-name", FF_VARIANT_TYPE_STRING).strValue;
cursorTheme = ffSettingsGet(instance, "/org/cinnamon/desktop/interface/cursor-theme", "org.cinnamon.desktop.interface", NULL, "cursor-theme", FF_VARIANT_TYPE_STRING).strValue;
cursorSize = ffSettingsGet(instance, "/org/cinnamon/desktop/interface/cursor-size", "org.cinnamon.desktop.interface", NULL, "cursor-size", FF_VARIANT_TYPE_INT).intValue;
wallpaper = ffSettingsGet(instance, "/org/cinnamon/desktop/background/picture-uri", "org.cinnamon.desktop.background", NULL, "picture-uri", FF_VARIANT_TYPE_STRING).strValue;
}
else if(ffStrbufIgnCaseCompS(&wmde->dePrettyName, FF_DE_PRETTY_MATE) == 0)
{
@@ -79,6 +87,7 @@ static void detectGTKFromSettings(const FFinstance* instance, FFGTKResult* resul
fontName = ffSettingsGet(instance, "/org/mate/interface/font-name", "org.mate.interface", NULL, "font-name", FF_VARIANT_TYPE_STRING).strValue;
cursorTheme = ffSettingsGet(instance, "/org/mate/peripherals-mouse/cursor-theme", "org.mate.peripherals-mouse", NULL, "cursor-theme", FF_VARIANT_TYPE_STRING).strValue;
cursorSize = ffSettingsGet(instance, "/org/mate/peripherals-mouse/cursor-size", "org.mate.peripherals-mouse", NULL, "cursor-size", FF_VARIANT_TYPE_INT).intValue;
wallpaper = ffSettingsGet(instance, "/org/mate/desktop/background", "org.mate.background", NULL, "picture-filename", FF_VARIANT_TYPE_STRING).strValue;
}
else if(
ffStrbufIgnCaseCompS(&wmde->dePrettyName, FF_DE_PRETTY_GNOME) == 0 ||
@@ -90,10 +99,11 @@ static void detectGTKFromSettings(const FFinstance* instance, FFGTKResult* resul
fontName = ffSettingsGet(instance, "/org/gnome/desktop/interface/font-name", "org.gnome.desktop.interface", NULL, "font-name", FF_VARIANT_TYPE_STRING).strValue;
cursorTheme = ffSettingsGet(instance, "/org/gnome/desktop/interface/cursor-theme", "org.gnome.desktop.interface", NULL, "cursor-theme", FF_VARIANT_TYPE_STRING).strValue;
cursorSize = ffSettingsGet(instance, "/org/gnome/desktop/interface/cursor-size", "org.gnome.desktop.interface", NULL, "cursor-size", FF_VARIANT_TYPE_INT).intValue;
wallpaper = ffSettingsGet(instance, "/org/gnome/desktop/background/picture-uri", "org.gnome.desktop.background", NULL, "picture-uri", FF_VARIANT_TYPE_STRING).strValue;
}
ffThreadMutexUnlock(&mutex);
applyGTKSettings(result, themeName, iconsName, fontName, cursorTheme, cursorSize);
applyGTKSettings(result, themeName, iconsName, fontName, cursorTheme, cursorSize, wallpaper);
}
static void detectGTKFromConfigFile(const char* filename, FFGTKResult* result)
@@ -184,6 +194,7 @@ static void detectGTK(const FFinstance* instance, const char* version, FFGTKResu
ffStrbufInit(&result.font); \
ffStrbufInit(&result.cursor); \
ffStrbufInit(&result.cursorSize); \
ffStrbufInit(&result.wallpaper); \
detectGTK(instance, #version, &result); \
ffThreadMutexUnlock(&mutex); \
return &result;
+2
View File
@@ -12,6 +12,7 @@ typedef struct FFGTKResult
FFstrbuf font;
FFstrbuf cursor;
FFstrbuf cursorSize;
FFstrbuf wallpaper;
} FFGTKResult;
typedef struct FFQtResult
@@ -20,6 +21,7 @@ typedef struct FFQtResult
FFstrbuf colorScheme;
FFstrbuf icons;
FFstrbuf font;
FFstrbuf wallpaper;
} FFQtResult;
const FFGTKResult* ffDetectGTK2(const FFinstance* instance);
+10 -1
View File
@@ -13,7 +13,8 @@ static inline bool allValuesSet(const FFQtResult* result)
result->widgetStyle.length > 0 &&
result->colorScheme.length > 0 &&
result->icons.length > 0 &&
result->font.length > 0;
result->font.length > 0 &&
result->wallpaper.length > 0;
}
typedef enum PlasmaCategory
@@ -96,6 +97,11 @@ static void detectPlasma(const FFinstance* instance, FFQtResult* result)
if(detectPlasmaFromFile(baseDir.chars, result))
foundAFile = true;
ffStrbufSet(&baseDir, configDir);
ffStrbufAppendS(&baseDir, "plasma-org.kde.plasma.desktop-appletsrc");
ffParsePropFile(baseDir.chars, "Image=", &result->wallpaper);
if(allValuesSet(result))
{
ffStrbufDestroy(&baseDir);
@@ -129,6 +135,8 @@ static void detectLXQt(const FFinstance* instance, FFQtResult* result)
{"icon_theme = ", &result->icons},
{"font = ", &result->font}
});
ffParsePropFileConfig(instance, "pcmanfm-qt/lxqt/settings.conf", "Wallpaper=", &result->wallpaper);
}
const FFQtResult* ffDetectQt(const FFinstance* instance)
@@ -149,6 +157,7 @@ const FFQtResult* ffDetectQt(const FFinstance* instance)
ffStrbufInit(&result.colorScheme);
ffStrbufInit(&result.icons);
ffStrbufInit(&result.font);
ffStrbufInit(&result.wallpaper);
const FFDisplayServerResult* wmde = ffConnectDisplayServer(instance);
+4
View File
@@ -112,6 +112,10 @@ static const char* getProductName(const FFstrbuf* hwModel)
else if(ffStrbufStartsWithS(hwModel, "Mac"))
{
const char* version = hwModel->chars + strlen("Mac");
if(strEqual(version, "14,15")) return "MacBook Air (15-inch, M2, 2023)";
if(strEqual(version, "14,14")) return "Mac Studio (M2 Max, 2023, Two USB-C front ports)";
if(strEqual(version, "14,13")) return "Mac Studio (M2 Ultra, 2023, Two Thunderbolt 4 front ports)";
if(strEqual(version, "14,8")) return "Mac Pro (2023)";
if(strEqual(version, "14,6") ||
strEqual(version, "14,10")) return "MacBook Pro (16-inch, 2023)";
if(strEqual(version, "14,5") ||
+10
View File
@@ -0,0 +1,10 @@
#pragma once
#ifndef FF_INCLUDED_detection_icons
#define FF_INCLUDED_detection_icons
#include "fastfetch.h"
const char* ffDetectIcons(const FFinstance* instance, FFstrbuf* result);
#endif
+36
View File
@@ -0,0 +1,36 @@
#include "icons.h"
#include "common/parsing.h"
#include "detection/gtk_qt/gtk_qt.h"
#include "detection/displayserver/displayserver.h"
const char* ffDetectIcons(const FFinstance* instance, FFstrbuf* result)
{
const FFDisplayServerResult* wmde = ffConnectDisplayServer(instance);
if(ffStrbufIgnCaseCompS(&wmde->wmProtocolName, FF_WM_PROTOCOL_TTY) == 0)
return "Icons aren't supported in TTY";
const FFstrbuf* plasma = &ffDetectQt(instance)->icons;
const FFstrbuf* gtk2 = &ffDetectGTK2(instance)->icons;
const FFstrbuf* gtk3 = &ffDetectGTK3(instance)->icons;
const FFstrbuf* gtk4 = &ffDetectGTK4(instance)->icons;
if(plasma->length == 0 && gtk2->length == 0 && gtk3->length == 0 && gtk4->length == 0)
return "No icons could be found";
FF_STRBUF_AUTO_DESTROY gtkPretty;
ffStrbufInit(&gtkPretty);
ffParseGTK(&gtkPretty, gtk2, gtk3, gtk4);
if(plasma->length > 0)
{
ffStrbufAppend(result, plasma);
ffStrbufAppendS(result, " [QT]");
if(gtkPretty.length > 0)
ffStrbufAppendS(result, ", ");
}
ffStrbufAppend(result, &gtkPretty);
return NULL;
}
+6
View File
@@ -0,0 +1,6 @@
#include "icons.h"
const char* ffDetectIcons(FF_MAYBE_UNUSED const FFinstance* instance, FF_MAYBE_UNUSED FFstrbuf* result)
{
return "Not supported on this platform";
}
+33
View File
@@ -0,0 +1,33 @@
#include "icons.h"
#include "util/windows/registry.h"
const char* ffDetectIcons(FF_MAYBE_UNUSED const FFinstance* instance, FFstrbuf* result)
{
FF_HKEY_AUTO_DESTROY hKey = NULL;
if(!ffRegOpenKeyForRead(HKEY_CURRENT_USER, L"Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\HideDesktopIcons\\ClassicStartMenu", &hKey, NULL))
return "ffRegOpenKeyForRead(Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\HideDesktopIcons\\ClassicStartMenu) failed";
// Whether these icons are hidden
uint32_t ThisPC = 0, UsersFiles = 0, RemoteNetwork = 0, RecycleBin = 0, ControlPanel = 0;
ffRegReadUint(hKey, L"{20D04FE0-3AEA-1069-A2D8-08002B30309D}", &ThisPC, NULL);
ffRegReadUint(hKey, L"{59031a47-3f72-44a7-89c5-5595fe6b30ee}", &UsersFiles, NULL);
ffRegReadUint(hKey, L"{F02C1A0D-BE21-4350-88B0-7367FC96EF3C}", &RemoteNetwork, NULL);
ffRegReadUint(hKey, L"{645FF040-5081-101B-9F08-00AA002F954E}", &RecycleBin, NULL);
ffRegReadUint(hKey, L"{5399E694-6CE5-4D6C-8FCE-1D8870FDCBA0}", &ControlPanel, NULL);
if (!ThisPC)
ffStrbufAppendS(result, "This PC, ");
if (!UsersFiles)
ffStrbufAppendS(result, "User's Files, ");
if (!RemoteNetwork)
ffStrbufAppendS(result, "Remote Network, ");
if (!RecycleBin)
ffStrbufAppendS(result, "Recycle Bin, ");
if (!ControlPanel)
ffStrbufAppendS(result, "Control Panel");
ffStrbufTrimRight(result, ' ');
ffStrbufTrimRight(result, ',');
return NULL;
}
+3 -2
View File
@@ -8,8 +8,9 @@
typedef struct FFLocalIpResult
{
FFstrbuf name;
FFstrbuf addr;
bool ipv6;
FFstrbuf ipv4;
FFstrbuf ipv6;
FFstrbuf mac;
} FFLocalIpResult;
const char* ffDetectLocalIps(const FFinstance* instance, FFlist* results);
+65 -16
View File
@@ -2,21 +2,48 @@
#include <string.h>
#include <ctype.h>
#include <net/if.h>
#include <ifaddrs.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <net/if.h>
#ifdef __FreeBSD__
#include <sys/socket.h> // FreeBSD needs this for AF_INET
#if defined(__FreeBSD__) || defined(__APPLE__)
#include <net/if_dl.h>
#else
#include <linux/if_packet.h>
#endif
static void addNewIp(FFlist* list, const char* name, const char* addr, bool ipv6)
static void addNewIp(FFlist* list, const char* name, const char* addr, int type)
{
FFLocalIpResult* ip = (FFLocalIpResult*) ffListAdd(list);
ffStrbufInitS(&ip->name, name);
ffStrbufInitS(&ip->addr, addr);
ip->ipv6 = ipv6;
FFLocalIpResult* ip = NULL;
FF_LIST_FOR_EACH(FFLocalIpResult, temp, *list)
{
if (!ffStrbufEqualS(&temp->name, name)) continue;
ip = temp;
break;
}
if (!ip)
{
ip = (FFLocalIpResult*) ffListAdd(list);
ffStrbufInitS(&ip->name, name);
ffStrbufInit(&ip->ipv4);
ffStrbufInit(&ip->ipv6);
ffStrbufInit(&ip->mac);
}
switch (type)
{
case AF_INET:
ffStrbufSetS(&ip->ipv4, addr);
break;
case AF_INET6:
ffStrbufSetS(&ip->ipv6, addr);
break;
case -1:
ffStrbufSetS(&ip->mac, addr);
break;
}
}
const char* ffDetectLocalIps(const FFinstance* instance, FFlist* results)
@@ -30,8 +57,7 @@ const char* ffDetectLocalIps(const FFinstance* instance, FFlist* results)
if (!ifa->ifa_addr || !(ifa->ifa_flags & IFF_RUNNING))
continue;
// loop back
if (strncmp(ifa->ifa_name, "lo", 2) == 0 && (ifa->ifa_name[2] == '\0' || isdigit(ifa->ifa_name[2])) && !instance->config.localIpShowLoop)
if ((ifa->ifa_flags & IFF_LOOPBACK) && !(instance->config.localIpShowType & FF_LOCALIP_TYPE_LOOP_BIT))
continue;
if (instance->config.localIpNamePrefix.length && strncmp(ifa->ifa_name, instance->config.localIpNamePrefix.chars, instance->config.localIpNamePrefix.length) != 0)
@@ -39,26 +65,49 @@ const char* ffDetectLocalIps(const FFinstance* instance, FFlist* results)
if (ifa->ifa_addr->sa_family == AF_INET)
{
// IPv4
if (!instance->config.localIpShowIpV4)
if (!(instance->config.localIpShowType & FF_LOCALIP_TYPE_IPV4_BIT))
continue;
struct sockaddr_in* ipv4 = (struct sockaddr_in*) ifa->ifa_addr;
char addressBuffer[INET_ADDRSTRLEN];
inet_ntop(AF_INET, &ipv4->sin_addr, addressBuffer, INET_ADDRSTRLEN);
addNewIp(results, ifa->ifa_name, addressBuffer, false);
addNewIp(results, ifa->ifa_name, addressBuffer, AF_INET);
}
else if (ifa->ifa_addr->sa_family == AF_INET6)
{
// IPv6
if (!instance->config.localIpShowIpV6)
if (!(instance->config.localIpShowType & FF_LOCALIP_TYPE_IPV6_BIT))
continue;
struct sockaddr_in6* ipv6 = (struct sockaddr_in6 *)ifa->ifa_addr;
char addressBuffer[INET6_ADDRSTRLEN];
inet_ntop(AF_INET6, &ipv6->sin6_addr, addressBuffer, INET6_ADDRSTRLEN);
addNewIp(results, ifa->ifa_name, addressBuffer, true);
addNewIp(results, ifa->ifa_name, addressBuffer, AF_INET6);
}
#if defined(__FreeBSD__) || defined(__APPLE__)
else if (ifa->ifa_addr->sa_family == AF_LINK)
{
if (!(instance->config.localIpShowType & FF_LOCALIP_TYPE_MAC_BIT))
continue;
char addressBuffer[32];
uint8_t* ptr = (uint8_t*) LLADDR((struct sockaddr_dl *)ifa->ifa_addr);
snprintf(addressBuffer, sizeof(addressBuffer), "%02x:%02x:%02x:%02x:%02x:%02x",
ptr[0], ptr[1], ptr[2], ptr[3], ptr[4], ptr[5]);
addNewIp(results, ifa->ifa_name, addressBuffer, -1);
}
#else
else if (ifa->ifa_addr->sa_family == AF_PACKET)
{
if (!(instance->config.localIpShowType & FF_LOCALIP_TYPE_MAC_BIT))
continue;
char addressBuffer[32];
uint8_t* ptr = ((struct sockaddr_ll *)ifa->ifa_addr)->sll_addr;
snprintf(addressBuffer, sizeof(addressBuffer), "%02x:%02x:%02x:%02x:%02x:%02x",
ptr[0], ptr[1], ptr[2], ptr[3], ptr[4], ptr[5]);
addNewIp(results, ifa->ifa_name, addressBuffer, -1);
}
#endif
}
if (ifAddrStruct) freeifaddrs(ifAddrStruct);
+53 -24
View File
@@ -1,21 +1,45 @@
#include <winsock2.h>
#include <ws2tcpip.h>
#include <iphlpapi.h>
#include <wchar.h>
#include "util/mallocHelper.h"
#include "util/windows/unicode.h"
#include "localip.h"
static void addNewIp(FFlist* list, const char* name, const char* addr, bool ipv6)
static void addNewIp(FFlist* list, const char* name, const char* value, int type, bool newIp)
{
FFLocalIpResult* ip = (FFLocalIpResult*) ffListAdd(list);
ffStrbufInitS(&ip->name, name);
ffStrbufInitS(&ip->addr, addr);
ip->ipv6 = ipv6;
FFLocalIpResult* ip = NULL;
if (newIp)
{
ip = (FFLocalIpResult*) ffListAdd(list);
ffStrbufInitS(&ip->name, name);
ffStrbufInit(&ip->ipv4);
ffStrbufInit(&ip->ipv6);
ffStrbufInit(&ip->mac);
}
else
{
ip = ffListGet(list, list->length - 1);
}
switch (type)
{
case AF_INET:
ffStrbufSetS(&ip->ipv4, value);
break;
case AF_INET6:
ffStrbufSetS(&ip->ipv6, value);
break;
case -1:
ffStrbufSetS(&ip->mac, value);
break;
}
}
const char* ffDetectLocalIps(const FFinstance* instance, FFlist* results)
{
IP_ADAPTER_ADDRESSES* adapter_addresses = NULL;
IP_ADAPTER_ADDRESSES* FF_AUTO_FREE adapter_addresses = NULL;
// Start with a 16 KB buffer and resize if needed -
// multiple attempts in case interfaces change while
@@ -27,11 +51,10 @@ const char* ffDetectLocalIps(const FFinstance* instance, FFlist* results)
assert(adapter_addresses);
DWORD error = GetAdaptersAddresses(
AF_UNSPEC,
GAA_FLAG_SKIP_ANYCAST |
GAA_FLAG_SKIP_MULTICAST |
GAA_FLAG_SKIP_DNS_SERVER |
GAA_FLAG_SKIP_FRIENDLY_NAME,
instance->config.localIpShowType & FF_LOCALIP_TYPE_IPV4_BIT
? instance->config.localIpShowType & FF_LOCALIP_TYPE_IPV6_BIT ? AF_UNSPEC : AF_INET
: AF_INET6,
GAA_FLAG_SKIP_ANYCAST | GAA_FLAG_SKIP_MULTICAST | GAA_FLAG_SKIP_DNS_SERVER,
NULL,
adapter_addresses,
&adapter_addresses_buffer_size);
@@ -47,41 +70,47 @@ const char* ffDetectLocalIps(const FFinstance* instance, FFlist* results)
// Iterate through all of the adapters
for (IP_ADAPTER_ADDRESSES* adapter = adapter_addresses; adapter; adapter = adapter->Next)
{
if (adapter->IfType == IF_TYPE_SOFTWARE_LOOPBACK && !instance->config.localIpShowLoop)
bool isLoop = adapter->IfType == IF_TYPE_SOFTWARE_LOOPBACK;
if (isLoop && !(instance->config.localIpShowType & FF_LOCALIP_TYPE_LOOP_BIT))
continue;
bool newIp = true;
char name[128];
WideCharToMultiByte(CP_UTF8, 0, adapter->FriendlyName, -1, name, sizeof(name), NULL, NULL);
if (instance->config.localIpNamePrefix.length && strncmp(name, instance->config.localIpNamePrefix.chars, instance->config.localIpNamePrefix.length) != 0)
continue;
if (instance->config.localIpShowType & FF_LOCALIP_TYPE_MAC_BIT && adapter->PhysicalAddressLength == 6)
{
char addressBuffer[32];
uint8_t* ptr = adapter->PhysicalAddress;
snprintf(addressBuffer, sizeof(addressBuffer), "%02x:%02x:%02x:%02x:%02x:%02x",
ptr[0], ptr[1], ptr[2], ptr[3], ptr[4], ptr[5]);
addNewIp(results, name, addressBuffer, -1, newIp);
newIp = false;
}
for (IP_ADAPTER_UNICAST_ADDRESS* ifa = adapter->FirstUnicastAddress; ifa; ifa = ifa->Next)
{
if (ifa->Address.lpSockaddr->sa_family == AF_INET)
{
// IPv4
if (!instance->config.localIpShowIpV4)
continue;
SOCKADDR_IN* ipv4 = (SOCKADDR_IN*) ifa->Address.lpSockaddr;
char addressBuffer[INET_ADDRSTRLEN];
inet_ntop(AF_INET, &ipv4->sin_addr, addressBuffer, INET_ADDRSTRLEN);
addNewIp(results, name, addressBuffer, false);
addNewIp(results, name, addressBuffer, AF_INET, newIp);
newIp = false;
}
else if (ifa->Address.lpSockaddr->sa_family == AF_INET6)
{
// IPv6
if (!instance->config.localIpShowIpV6)
continue;
SOCKADDR_IN6* ipv6 = (SOCKADDR_IN6*) ifa->Address.lpSockaddr;
char addressBuffer[INET6_ADDRSTRLEN];
inet_ntop(AF_INET6, &ipv6->sin6_addr, addressBuffer, INET6_ADDRSTRLEN);
addNewIp(results, name, addressBuffer, true);
addNewIp(results, name, addressBuffer, AF_INET6, newIp);
newIp = false;
}
}
}
free(adapter_addresses);
return NULL;
}
+1 -1
View File
@@ -7,7 +7,7 @@ const FFMediaResult* ffDetectMedia(const FFinstance* instance)
{
FF_DETECTION_INTERNAL_GUARD(FFMediaResult,
ffStrbufInitA(&result.error, 0);
ffStrbufInit(&result.busNameShort);
ffStrbufInit(&result.playerId);
ffStrbufInit(&result.player);
ffStrbufInit(&result.song);
ffStrbufInit(&result.artist);
+1 -1
View File
@@ -8,7 +8,7 @@
typedef struct FFMediaResult
{
FFstrbuf error;
FFstrbuf busNameShort; //e.g. plasma-browser-integration
FFstrbuf playerId; // Bus name on Linux, app bundle name on macOS. e.g. plasma-browser-integration
FFstrbuf player; // e.g. Google Chrome
FFstrbuf song;
FFstrbuf artist;
+3 -3
View File
@@ -57,17 +57,17 @@ static const char* getMedia(FFMediaResult* result)
if (identifier == nil)
identifier = MRNowPlayingClientGetParentAppBundleIdentifier(clientObj);
if (identifier != nil)
ffCfStrGetString(identifier, &result->busNameShort);
ffCfStrGetString(identifier, &result->playerId);
}
dispatch_group_leave(group);
});
dispatch_group_wait(group, DISPATCH_TIME_FOREVER);
if(result->busNameShort.length > 0)
if(result->playerId.length > 0)
{
char buf[128];
snprintf(buf, sizeof(buf), "name of app id \"%s\"", result->busNameShort.chars);
snprintf(buf, sizeof(buf), "name of app id \"%s\"", result->playerId.chars);
ffOsascript(buf, &result->player);
}
+2 -2
View File
@@ -87,14 +87,14 @@ static bool getBusProperties(FFDBusData* data, const char* busName, FFMediaResul
}
//Set short bus name
ffStrbufAppendS(&result->busNameShort, busName + sizeof(FF_DBUS_MPRIS_PREFIX) - 1);
ffStrbufAppendS(&result->playerId, busName + sizeof(FF_DBUS_MPRIS_PREFIX) - 1);
//We found a song, get the player name
ffDBusGetPropertyString(data, busName, "/org/mpris/MediaPlayer2", "org.mpris.MediaPlayer2", "Identity", &result->player);
if(result->player.length == 0)
ffDBusGetPropertyString(data, busName, "/org/mpris/MediaPlayer2", "org.mpris.MediaPlayer2", "DesktopEntry", &result->player);
if(result->player.length == 0)
ffStrbufAppend(&result->player, &result->busNameShort);
ffStrbufAppend(&result->player, &result->playerId);
return true;
}
+8 -2
View File
@@ -3,8 +3,14 @@
#ifndef FF_INCLUDED_detection_memory_memory
#define FF_INCLUDED_detection_memory_memory
#include "detection/storage.h"
#include "fastfetch.h"
void ffDetectMemory(FFMemoryStorage* result);
typedef struct FFMemoryResult
{
uint64_t bytesUsed;
uint64_t bytesTotal;
} FFMemoryResult;
const char* ffDetectMemory(FFMemoryResult* result);
#endif
+7 -13
View File
@@ -3,31 +3,25 @@
#include <string.h>
#include <mach/mach.h>
#include <sys/sysctl.h>
#include <unistd.h>
void ffDetectMemory(FFMemoryStorage* ram)
const char* ffDetectMemory(FFMemoryResult* ram)
{
size_t length = sizeof(ram->bytesTotal);
if (sysctl((int[]){ CTL_HW, HW_MEMSIZE }, 2, &ram->bytesTotal, &length, NULL, 0))
{
ffStrbufAppendS(&ram->error, "Failed to read hw.memsize");
return;
}
return "Failed to read hw.memsize";
uint32_t pagesize;
length = sizeof(pagesize);
if (sysctl((int[]){ CTL_HW, HW_PAGESIZE }, 2, &pagesize, &length, NULL, 0))
{
ffStrbufAppendS(&ram->error, "Failed to read hw.pagesize");
return;
}
return "Failed to read hw.pagesize";
mach_msg_type_number_t count = HOST_VM_INFO64_COUNT;
vm_statistics64_data_t vmstat;
if(host_statistics64(mach_host_self(), HOST_VM_INFO64, (host_info64_t) (&vmstat), &count) != KERN_SUCCESS)
{
ffStrbufAppendS(&ram->error, "Failed to read host_statistics64");
return;
}
return "Failed to read host_statistics64";
ram->bytesUsed = ((uint64_t) vmstat.active_count + vmstat.wire_count) * pagesize;
return NULL;
}
+16 -17
View File
@@ -1,24 +1,23 @@
#include "memory.h"
#include "common/sysctl.h"
void ffDetectMemory(FFMemoryStorage* ram)
const char* ffDetectMemory(FFMemoryResult* ram)
{
uint32_t pageSize = (uint32_t) ffSysctlGetInt("hw.pagesize", 0);
if(pageSize == 0)
{
ffStrbufAppendS(&ram->error, "Failed to read hw.pagesize");
return;
}
uint64_t length = sizeof(ram->bytesTotal);
if (sysctl((int[]){ CTL_HW, HW_PHYSMEM }, 2, &ram->bytesTotal, &length, NULL, 0))
return "Failed to read hw.physmem";
ram->bytesTotal = (uint64_t) ffSysctlGetInt64("vm.stats.vm.v_page_count", 0) * pageSize;
if(ram->bytesTotal == 0)
{
ffStrbufAppendS(&ram->error, "Failed to read vm.stats.vm.v_page_count");
return;
}
uint32_t pageSize;
length = sizeof(pageSize);
if (sysctl((int[]){ CTL_HW, HW_PAGESIZE }, 2, &pageSize, &length, NULL, 0))
return "Failed to read hw.pagesize";
ram->bytesUsed = ram->bytesTotal
- (uint64_t) ffSysctlGetInt64("vm.stats.vm.v_free_count", 0) * pageSize
- (uint64_t) ffSysctlGetInt64("vm.stats.vm.v_inactive_count", 0) * pageSize
;
// vm.stats.vm.* are int values
int32_t pagesFree = ffSysctlGetInt("vm.stats.vm.v_free_count", 0)
+ ffSysctlGetInt("vm.stats.vm.v_inactive_count", 0)
+ ffSysctlGetInt("vm.stats.vm.v_cache_count", 0);
ram->bytesUsed = ram->bytesTotal - (uint64_t) pagesFree * pageSize;
return NULL;
}
+7 -10
View File
@@ -1,18 +1,16 @@
#include "memory.h"
#include "util/mallocHelper.h"
#include <stdlib.h>
#include <string.h>
void ffDetectMemory(FFMemoryStorage* ram)
const char* ffDetectMemory(FFMemoryResult* ram)
{
FILE* meminfo = fopen("/proc/meminfo", "r");
if(meminfo == NULL)
{
ffStrbufAppendS(&ram->error, "Failed to open /proc/meminfo");
return;
}
return "Failed to open /proc/meminfo";
char* line = NULL;
char* FF_AUTO_FREE line = NULL;
size_t len = 0;
uint32_t memTotal = 0,
@@ -32,14 +30,13 @@ void ffDetectMemory(FFMemoryStorage* ram)
sscanf(line, "SReclaimable: %u", &sReclaimable);
}
if(line != NULL)
free(line);
fclose(meminfo);
ram->bytesTotal = memTotal * (uint64_t) 1024;
if(ram->bytesTotal == 0)
ffStrbufAppendS(&ram->error, "Failed to read MemTotal");
return "Failed to read MemTotal";
else
ram->bytesUsed = (memTotal + shmem - memFree - buffers - cached - sReclaimable) * (uint64_t) 1024;
return NULL;
}
+6 -5
View File
@@ -1,15 +1,16 @@
#include "memory.h"
void ffDetectMemory(FFMemoryStorage* ram)
#include <windows.h>
const char* ffDetectMemory(FFMemoryResult* ram)
{
MEMORYSTATUSEX statex = {
.dwLength = sizeof(statex),
};
if (!GlobalMemoryStatusEx(&statex))
{
ffStrbufAppendS(&ram->error, "GlobalMemoryStatusEx() failed");
return;
}
return "GlobalMemoryStatusEx() failed";
ram->bytesTotal = statex.ullTotalPhys;
ram->bytesUsed = statex.ullTotalPhys - statex.ullAvailPhys;
return NULL;
}
+102
View File
@@ -0,0 +1,102 @@
#include "detection/opencl/opencl.h"
#if defined(FF_HAVE_OPENCL) || defined(__APPLE__)
#include "common/library.h"
#include "common/parsing.h"
#include "util/stringUtils.h"
#include <string.h>
#define CL_TARGET_OPENCL_VERSION 100
#ifdef FF_HAVE_OPENCL
#include <CL/cl.h>
#else
#include <OpenCL/cl.h>
#endif
typedef struct OpenCLData
{
FF_LIBRARY_SYMBOL(clGetPlatformIDs)
FF_LIBRARY_SYMBOL(clGetDeviceIDs)
FF_LIBRARY_SYMBOL(clGetDeviceInfo)
} OpenCLData;
static const char* openCLHandleData(OpenCLData* data, FFOpenCLResult* result)
{
cl_platform_id platformID;
cl_uint numPlatforms;
data->ffclGetPlatformIDs(1, &platformID, &numPlatforms);
if(numPlatforms == 0)
return "clGetPlatformIDs returned 0 platforms";
cl_device_id deviceID;
cl_uint numDevices;
data->ffclGetDeviceIDs(platformID, CL_DEVICE_TYPE_GPU, 1, &deviceID, &numDevices);
if(numDevices == 0)
data->ffclGetDeviceIDs(platformID, CL_DEVICE_TYPE_ALL, 1, &deviceID, &numDevices);
if(numDevices == 0)
return "clGetDeviceIDs returned 0 devices";
char version[64];
data->ffclGetDeviceInfo(deviceID, CL_DEVICE_VERSION, sizeof(version), version, NULL);
if(!ffStrSet(version))
return "clGetDeviceInfo returned NULL or empty string";
const char* versionPretty = version;
const char* prefix = "OpenCL ";
if(strncasecmp(version, prefix, sizeof(prefix) - 1) == 0)
versionPretty = version + sizeof(prefix) - 1;
ffStrbufSetS(&result->version, versionPretty);
ffStrbufEnsureFree(&result->device, 128);
data->ffclGetDeviceInfo(deviceID, CL_DEVICE_NAME, result->device.allocated, result->device.chars, NULL);
ffStrbufRecalculateLength(&result->device);
ffStrbufEnsureFree(&result->vendor, 32);
data->ffclGetDeviceInfo(deviceID, CL_DEVICE_VENDOR, result->vendor.allocated, result->vendor.chars, NULL);
ffStrbufRecalculateLength(&result->vendor);
return NULL;
}
#endif // defined(FF_HAVE_OPENCL) || defined(__APPLE__)
const char* ffDetectOpenCL(FFinstance* instance, FFOpenCLResult* result)
{
#ifdef FF_HAVE_OPENCL
OpenCLData data;
FF_LIBRARY_LOAD(opencl, &instance->config.libOpenCL, "dlopen libOpenCL"FF_LIBRARY_EXTENSION" failed",
#ifdef _WIN32
"OpenCL"FF_LIBRARY_EXTENSION, -1,
#endif
"libOpenCL"FF_LIBRARY_EXTENSION, 1
);
FF_LIBRARY_LOAD_SYMBOL_VAR_MESSAGE(opencl, data, clGetPlatformIDs);
FF_LIBRARY_LOAD_SYMBOL_VAR_MESSAGE(opencl, data, clGetDeviceIDs);
FF_LIBRARY_LOAD_SYMBOL_VAR_MESSAGE(opencl, data, clGetDeviceInfo);
return openCLHandleData(&data, result);
#elif defined(__APPLE__) // FF_HAVE_OPENCL
FF_UNUSED(instance);
OpenCLData data;
data.ffclGetPlatformIDs = clGetPlatformIDs;
data.ffclGetDeviceIDs = clGetDeviceIDs;
data.ffclGetDeviceInfo = clGetDeviceInfo;
return openCLHandleData(&data, result);
#else
FF_UNUSED(instance, result);
return "Fastfetch was build without OpenCL support";
#endif // FF_HAVE_OPENCL
}
+17
View File
@@ -0,0 +1,17 @@
#pragma once
#ifndef FF_INCLUDED_detection_opencl_opencl
#define FF_INCLUDED_detection_opencl_opencl
#include "fastfetch.h"
typedef struct FFOpenCLResult
{
FFstrbuf version;
FFstrbuf device;
FFstrbuf vendor;
} FFOpenCLResult;
const char* ffDetectOpenCL(FFinstance* instance, FFOpenCLResult* result);
#endif
-1
View File
@@ -2,7 +2,6 @@
#include "common/printing.h"
#include "opengl.h"
#define WIN32_LEAN_AND_MEAN 1
#include <Windows.h>
#include <GL/gl.h>
#ifndef GL_SHADING_LANGUAGE_VERSION // For WGL
+48 -2
View File
@@ -24,7 +24,52 @@ static void parseSystemVersion(FFOSResult* os)
ffStrbufInitS(&os->buildID, value.UTF8String);
}
void parseOSXSoftwareLicense(FFOSResult* os)
static bool detectOSCodeName(FFOSResult* os)
{
// https://en.wikipedia.org/wiki/MacOS_version_history
char* str_end;
const char* version = os->version.chars;
unsigned long num = strtoul(version, &str_end, 10);
if (str_end == version) return false;
switch (num)
{
case 14: ffStrbufAppendS(&os->codename, "Sonoma"); return true;
case 13: ffStrbufAppendS(&os->codename, "Ventura"); return true;
case 12: ffStrbufAppendS(&os->codename, "Monterey"); return true;
case 11: ffStrbufAppendS(&os->codename, "Big Sur"); return true;
case 10: {
version = str_end + 1;
num = strtoul(version, &str_end, 10);
if (str_end == version) return false;
switch (num)
{
case 16: ffStrbufAppendS(&os->codename, "Big Sur"); return true;
case 15: ffStrbufAppendS(&os->codename, "Catalina"); return true;
case 14: ffStrbufAppendS(&os->codename, "Mojave"); return true;
case 13: ffStrbufAppendS(&os->codename, "High Sierra"); return true;
case 12: ffStrbufAppendS(&os->codename, "Sierra"); return true;
case 11: ffStrbufAppendS(&os->codename, "El Capitan"); return true;
case 10: ffStrbufAppendS(&os->codename, "Yosemite"); return true;
case 9: ffStrbufAppendS(&os->codename, "Mavericks"); return true;
case 8: ffStrbufAppendS(&os->codename, "Mountain Lion"); return true;
case 7: ffStrbufAppendS(&os->codename, "Lion"); return true;
case 6: ffStrbufAppendS(&os->codename, "Snow Leopard"); return true;
case 5: ffStrbufAppendS(&os->codename, "Leopard"); return true;
case 4: ffStrbufAppendS(&os->codename, "Tiger"); return true;
case 3: ffStrbufAppendS(&os->codename, "Panther"); return true;
case 2: ffStrbufAppendS(&os->codename, "Jaguar"); return true;
case 1: ffStrbufAppendS(&os->codename, "Puma"); return true;
case 0: ffStrbufAppendS(&os->codename, "Cheetah"); return true;
}
}
}
return false;
}
static void parseOSXSoftwareLicense(FFOSResult* os)
{
FILE* rtf = fopen("/System/Library/CoreServices/Setup Assistant.app/Contents/Resources/en.lproj/OSXSoftwareLicense.rtf", "r");
if(rtf == NULL)
@@ -81,5 +126,6 @@ void ffDetectOSImpl(FFOSResult* os, const FFinstance* instance)
ffStrbufAppend(&os->prettyName, &os->name);
ffStrbufAppend(&os->versionID, &os->version);
parseOSXSoftwareLicense(os);
if(!detectOSCodeName(os))
parseOSXSoftwareLicense(os);
}
+5 -13
View File
@@ -1,5 +1,6 @@
extern "C" {
#include "os.h"
#include "common/library.h"
#include "util/windows/unicode.h"
}
#include "util/windows/wmi.hpp"
@@ -20,27 +21,18 @@ static const char* getOsNameByWmi(FFstrbuf* osName)
return "No WMI result returned";
}
static inline void wrapFreeLibrary(HMODULE* module)
{
if(*module)
FreeLibrary(*module);
}
PWSTR WINAPI BrandingFormatString(PCWSTR format);
static const char* getOsNameByWinbrand(FFstrbuf* osName)
{
//https://dennisbabkin.com/blog/?t=how-to-tell-the-real-version-of-windows-your-app-is-running-on#ver_string
if(HMODULE __attribute__((__cleanup__(wrapFreeLibrary))) hWinbrand = LoadLibraryW(L"winbrand.dll"))
{
auto BrandingFormatString = (PWSTR(WINAPI*)(PCWSTR))(void*)GetProcAddress(hWinbrand, "BrandingFormatString");
if(!BrandingFormatString)
return "GetProcAddress(BrandingFormatString) failed";
FF_LIBRARY_LOAD(winbrand, nullptr, "dlopen winbrand" FF_LIBRARY_EXTENSION " failed", "winbrand" FF_LIBRARY_EXTENSION, 1);
FF_LIBRARY_LOAD_SYMBOL_MESSAGE(winbrand, BrandingFormatString);
const wchar_t* rawName = BrandingFormatString(L"%WINDOWS_LONG%");
const wchar_t* rawName = ffBrandingFormatString(L"%WINDOWS_LONG%");
ffStrbufSetWS(osName, rawName);
GlobalFree((HGLOBAL)rawName);
return NULL;
}
return "LoadLibraryW(winbrand.dll) failed";
}
extern "C"
+2 -1
View File
@@ -14,7 +14,8 @@ typedef struct FFPackagesResult
uint32_t dpkg;
uint32_t emerge;
uint32_t eopkg;
uint32_t flatpak;
uint32_t flatpakSystem;
uint32_t flatpakUser;
uint32_t nixDefault;
uint32_t nixSystem;
uint32_t nixUser;
+20 -6
View File
@@ -135,7 +135,7 @@ static uint32_t getNixPackagesImpl(char* path)
FFstrbuf output;
ffStrbufInitA(&output, 128);
//https://github.com/LinusDierheimer/fastfetch/issues/195#issuecomment-1191748222
//https://github.com/fastfetch-cli/fastfetch/issues/195#issuecomment-1191748222
FFstrbuf command;
ffStrbufInitA(&command, 255);
ffStrbufAppendS(&command, "for x in $(nix-store --query --requisites ");
@@ -207,6 +207,19 @@ static uint32_t getSnap(FFstrbuf* baseDir)
return result > 0 ? result - 1 : 0;
}
static uint32_t getFlatpak(FFstrbuf* baseDir, const char* dirname)
{
uint32_t baseDirLength = baseDir->length;
ffStrbufAppendS(baseDir, dirname);
uint32_t result =
getNumElements(baseDir, "/app", DT_DIR) +
getNumElements(baseDir, "/runtime", DT_DIR);
ffStrbufSubstrBefore(baseDir, baseDirLength);
return result;
}
#ifdef FF_HAVE_RPM
#include "common/library.h"
#include <rpm/rpmlib.h>
@@ -258,7 +271,7 @@ static void getPackageCounts(const FFinstance* instance, FFstrbuf* baseDir, FFPa
packageCounts->dpkg += getNumStrings(baseDir, "/var/lib/dpkg/status", "Status: ");
packageCounts->emerge += countFilesRecursive(baseDir, "/var/db/pkg", "SIZE");
packageCounts->eopkg += getNumElements(baseDir, "/var/lib/eopkg/package", DT_DIR);
packageCounts->flatpak += getNumElements(baseDir, "/var/lib/flatpak/app", DT_DIR);
packageCounts->flatpakSystem += getFlatpak(baseDir, "/var/lib/flatpak");
packageCounts->nixDefault += getNixPackages(baseDir, "/nix/var/nix/profiles/default");
packageCounts->nixSystem += getNixPackages(baseDir, "/run/current-system");
packageCounts->pacman += getNumElements(baseDir, "/var/lib/pacman/local", DT_DIR);
@@ -266,6 +279,8 @@ static void getPackageCounts(const FFinstance* instance, FFstrbuf* baseDir, FFPa
packageCounts->rpm += getSQLite3Int(instance, baseDir, "/var/lib/rpm/rpmdb.sqlite", "SELECT count(blob) FROM Packages");
packageCounts->snap += getSnap(baseDir);
packageCounts->xbps += getXBPS(baseDir, "/var/db/xbps");
packageCounts->brewCask += getNumElements(baseDir, "/home/linuxbrew/.linuxbrew/Caskroom", DT_DIR);
packageCounts->brew += getNumElements(baseDir, "/home/linuxbrew/.linuxbrew/Cellar", DT_DIR);
}
static void getPackageCountsRegular(const FFinstance* instance, FFstrbuf* baseDir, FFPackagesResult* packageCounts)
@@ -314,11 +329,11 @@ static void getPackageCountsBedrock(const FFinstance* instance, FFstrbuf* baseDi
void ffDetectPackagesImpl(const FFinstance* instance, FFPackagesResult* result)
{
FFstrbuf baseDir;
FF_STRBUF_AUTO_DESTROY baseDir;
ffStrbufInitA(&baseDir, 512);
ffStrbufAppendS(&baseDir, FASTFETCH_TARGET_DIR_ROOT);
if(ffStrbufIgnCaseCompS(&(ffDetectOS(instance)->id), "bedrock") == 0)
if(ffStrbufIgnCaseEqualS(&ffDetectOS(instance)->id, "bedrock"))
getPackageCountsBedrock(instance, &baseDir, result);
else
getPackageCountsRegular(instance, &baseDir, result);
@@ -333,6 +348,5 @@ void ffDetectPackagesImpl(const FFinstance* instance, FFPackagesResult* result)
ffStrbufSet(&baseDir, &instance->state.platform.homeDir);
result->nixUser = getNixPackages(&baseDir, "/.nix-profile");
ffStrbufDestroy(&baseDir);
result->flatpakUser = getFlatpak(&baseDir, "/.local/share/flatpak");
}
+1 -1
View File
@@ -5,6 +5,6 @@
#include "fastfetch.h"
uint32_t ffDetectProcesses(FFstrbuf* error);
const char* ffDetectProcesses(uint32_t* result);
#endif
+5 -6
View File
@@ -6,15 +6,14 @@
#include <sys/user.h>
#endif
uint32_t ffDetectProcesses(FFstrbuf* error)
const char* ffDetectProcesses(uint32_t* result)
{
int request[] = {CTL_KERN, KERN_PROC, KERN_PROC_ALL};
size_t length;
if(sysctl(request, sizeof(request) / sizeof(*request), NULL, &length, NULL, 0) != 0)
{
ffStrbufAppendS(error, "sysctl() failed");
return 0;
}
return (uint32_t)(length / sizeof(struct kinfo_proc));
return "sysctl({CTL_KERN, KERN_PROC, KERN_PROC_ALL}) failed";
*result = (uint32_t)(length / sizeof(struct kinfo_proc));
return NULL;
}
+5 -3
View File
@@ -2,10 +2,12 @@
#include <sys/sysinfo.h>
uint32_t ffDetectProcesses(FFstrbuf* error)
const char* ffDetectProcesses(uint32_t* result)
{
struct sysinfo info;
if(sysinfo(&info) != 0)
ffStrbufAppendS(error, "sysinfo() failed");
return (uint32_t) info.procs;
return "sysinfo() failed";
*result = (uint32_t) info.procs;
return NULL;
}
@@ -0,0 +1,27 @@
#include "processes.h"
#include "util/mallocHelper.h"
#include <ntstatus.h>
#include <winternl.h>
const char* ffDetectProcesses(uint32_t* result)
{
ULONG size = 0;
if(NtQuerySystemInformation(SystemProcessInformation, NULL, 0, &size) != STATUS_INFO_LENGTH_MISMATCH)
return "NtQuerySystemInformation(SystemProcessInformation, NULL) failed";
size += sizeof(SystemProcessInformation) * 5; //What if new processes are created during two syscalls?
SYSTEM_PROCESS_INFORMATION* FF_AUTO_FREE pstart = (SYSTEM_PROCESS_INFORMATION*)malloc(size);
if(!pstart)
return "malloc(size) failed";
if(!NT_SUCCESS(NtQuerySystemInformation(SystemProcessInformation, pstart, size, NULL)))
return "NtQuerySystemInformation(SystemProcessInformation, pstart) failed";
*result = 1; //Init with 1 because we test for ptr->NextEntryOffset
for (SYSTEM_PROCESS_INFORMATION* ptr = pstart; ptr->NextEntryOffset; ptr = (SYSTEM_PROCESS_INFORMATION*)((uint8_t*)ptr + ptr->NextEntryOffset))
++*result;
return NULL;
}
@@ -1,64 +0,0 @@
extern "C" {
#include "processes.h"
#include "util/mallocHelper.h"
}
#ifdef FF_USE_WIN_NTAPI
#include <ntstatus.h>
#include <winternl.h>
uint32_t ffDetectProcesses(FFstrbuf* error)
{
ULONG size = 0;
if(NtQuerySystemInformation(SystemProcessInformation, nullptr, 0, &size) != STATUS_INFO_LENGTH_MISMATCH)
{
ffStrbufAppendS(error, "NtQuerySystemInformation(SystemProcessInformation, NULL) failed");
return 0;
}
size += sizeof(SystemProcessInformation) * 5; //What if new processes are created during two syscalls?
SYSTEM_PROCESS_INFORMATION* FF_AUTO_FREE pstart = (SYSTEM_PROCESS_INFORMATION*)malloc(size);
if(!pstart)
{
ffStrbufAppendF(error, "malloc(%u) failed", (unsigned)size);
return 0;
}
if(!NT_SUCCESS(NtQuerySystemInformation(SystemProcessInformation, pstart, size, nullptr)))
{
ffStrbufAppendS(error, "NtQuerySystemInformation(SystemProcessInformation, pstart) failed");
return 0;
}
uint32_t result = 1; //Init with 1 because we test for ptr->NextEntryOffset
for (auto ptr = pstart; ptr->NextEntryOffset; ptr = (SYSTEM_PROCESS_INFORMATION*)((uint8_t*)ptr + ptr->NextEntryOffset))
++result;
return result;
}
#else
#include "util/windows/wmi.hpp"
uint32_t ffDetectProcesses(FFstrbuf* error)
{
FFWmiQuery query(L"SELECT NumberOfProcesses FROM Win32_OperatingSystem", error);
if(!query)
return 0;
if(FFWmiRecord record = query.next())
{
uint64_t result = 0;
record.getUnsigned(L"NumberOfProcesses", &result);
return (uint32_t)result;
}
else
{
ffStrbufAppendS(error, "No Wmi result returned");
return 0;
}
}
#endif
+2
View File
@@ -5,6 +5,8 @@
#include "fastfetch.h"
#define FF_SOUND_VOLUME_UNKNOWN 255
typedef struct FFSoundDevice
{
FFstrbuf identifier;
+34 -1
View File
@@ -2,6 +2,11 @@
#include "util/apple/cf_helpers.h"
#include <CoreAudio/CoreAudio.h>
#include <AvailabilityMacros.h>
#ifndef MAC_OS_VERSION_12_0
#define kAudioObjectPropertyElementMain kAudioObjectPropertyElementMaster
#endif
const char* ffDetectSound(FF_MAYBE_UNUSED const FFinstance* instance, FFlist* devices /* List of FFSoundDevice */)
{
@@ -39,7 +44,7 @@ const char* ffDetectSound(FF_MAYBE_UNUSED const FFinstance* instance, FFlist* de
FFSoundDevice* device = (FFSoundDevice*) ffListAdd(devices);
device->main = deviceId == mainDeviceId;
device->active = false;
device->volume = 0;
device->volume = FF_SOUND_VOLUME_UNKNOWN;
ffStrbufInitF(&device->identifier, "%u", (unsigned) deviceId);
ffStrbufInit(&device->name);
@@ -62,6 +67,34 @@ const char* ffDetectSound(FF_MAYBE_UNUSED const FFinstance* instance, FFlist* de
kAudioObjectPropertyElementMain
}, 0, NULL, &dataSize, &volume) == kAudioHardwareNoError)
device->volume = (uint8_t) (volume * 100 + 0.5);
else
{
// Try detecting volume from channels
uint32_t channels[2];
dataSize = sizeof(channels);
if (AudioObjectGetPropertyData(deviceId, &(AudioObjectPropertyAddress){
kAudioDevicePropertyPreferredChannelsForStereo,
kAudioObjectPropertyScopeOutput,
kAudioObjectPropertyElementMain
}, 0, NULL, &dataSize, channels) == kAudioHardwareNoError)
{
dataSize = sizeof(volume);
if (AudioObjectGetPropertyData(deviceId, &(AudioObjectPropertyAddress){
kAudioDevicePropertyVolumeScalar,
kAudioObjectPropertyScopeOutput,
channels[0]
}, 0, NULL, &dataSize, &volume) == kAudioHardwareNoError)
{
float temp;
if (AudioObjectGetPropertyData(deviceId, &(AudioObjectPropertyAddress){
kAudioDevicePropertyVolumeScalar,
kAudioObjectPropertyScopeOutput,
channels[1]
}, 0, NULL, &dataSize, &temp) == kAudioHardwareNoError)
device->volume = (uint8_t) ((volume + temp) / 2 * 100 + 0.5);
}
}
}
}
CFStringRef name;
+1 -1
View File
@@ -77,7 +77,7 @@ static const char* detectSound(const FFinstance* instance, FFlist* devices)
return "Failed to connect to pulseaudio context";
}
int state;
pa_context_state_t state;
while((state = ffpa_context_get_state(context)) != PA_CONTEXT_READY)
{
if(!PA_CONTEXT_IS_GOOD(state))
+2 -4
View File
@@ -62,12 +62,10 @@ const char* ffDetectSound(FF_MAYBE_UNUSED const FFinstance* instance, FF_MAYBE_U
FFSoundDevice* device = (FFSoundDevice*) ffListAdd(devices);
device->main = wcscmp(mainDeviceId, immDeviceId) == 0;
device->active = !!(immState & DEVICE_STATE_ACTIVE);
device->volume = 0;
ffStrbufInit(&device->identifier);
device->volume = FF_SOUND_VOLUME_UNKNOWN;
ffStrbufInitWS(&device->identifier, immDeviceId);
ffStrbufInit(&device->name);
ffStrbufSetWS(&device->identifier, immDeviceId);
{
PROPVARIANT __attribute__((__cleanup__(PropVariantClear))) friendlyName;
PropVariantInit(&friendlyName);
-15
View File
@@ -1,15 +0,0 @@
#pragma once
#ifndef FF_INCLUDED_detection_storage
#define FF_INCLUDED_detection_storage
#include "fastfetch.h"
typedef struct FFMemoryStorage
{
FFstrbuf error;
uint64_t bytesUsed;
uint64_t bytesTotal;
} FFMemoryStorage;
#endif
+8 -2
View File
@@ -3,8 +3,14 @@
#ifndef FF_INCLUDED_detection_swap_swap
#define FF_INCLUDED_detection_swap_swap
#include "detection/storage.h"
#include "fastfetch.h"
void ffDetectSwap(FFMemoryStorage* result);
typedef struct FFSwapResult
{
uint64_t bytesUsed;
uint64_t bytesTotal;
} FFSwapResult;
const char* ffDetectSwap(FFSwapResult* result);
#endif
+3 -5
View File
@@ -3,16 +3,14 @@
#include <mach/mach.h>
#include <sys/sysctl.h>
void ffDetectSwap(FFMemoryStorage* swap)
const char* ffDetectSwap(FFSwapResult* swap)
{
struct xsw_usage xsw;
size_t size = sizeof(xsw);
if(sysctl((int[]){ CTL_VM, VM_SWAPUSAGE }, 2, &xsw, &size, NULL, 0) != 0)
{
ffStrbufAppendS(&swap->error, "Failed to read vm.swapusage");
return;
}
return "Failed to read vm.swapusage";
swap->bytesTotal = xsw.xsu_total;
swap->bytesUsed = xsw.xsu_used;
return NULL;
}

Some files were not shown because too many files have changed in this diff Show More