1 /*
2  *
3  * Conky, a system monitor, based on torsmo.
4  *
5  * Any original torsmo code is licensed under the BSD license.
6  * All code written since the fork of torsmo is licensed under the GPL.
7  * Please see COPYING for details.
8  *
9  * Copyright (c) 2021 Rogier Reerink
10  *  (See AUTHORS)
11  * All rights reserved.
12  *
13  * This program is free software: you can redistribute it and/or modify
14  * it under the terms of the GNU General Public License as published by
15  * the Free Software Foundation, either version 3 of the License, or
16  * (at your option) any later version.
17  *
18  * This program is distributed in the hope that it will be useful,
19  * but WITHOUT ANY WARRANTY; without even the implied warranty of
20  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
21  * GNU General Public License for more details.
22  *
23  * You should have received a copy of the GNU General Public License
24  * along with this program.  If not, see <https://www.gnu.org/licenses/>.
25  *
26  */
27 
28 #include "intel_backlight.h"
29 #include "logging.h"
30 
31 #define FS_BRIGHTNESS_MAX "/sys/class/backlight/intel_backlight/max_brightness"
32 #define FS_BRIGHTNESS_CURRENT "/sys/class/backlight/intel_backlight/brightness"
33 
34 struct backlight {
35   FILE *fp_max;
36   unsigned max;
37   FILE *fp_current;
38   unsigned current;
39 };
40 
open_backlight(struct backlight * bl)41 void open_backlight(struct backlight *bl) {
42   bl->fp_max = fopen(FS_BRIGHTNESS_MAX, "r");
43   if (bl->fp_max == NULL) {
44     NORM_ERR("Failed to open file: '" FS_BRIGHTNESS_MAX "'.");
45   }
46   bl->fp_current = fopen(FS_BRIGHTNESS_CURRENT, "r");
47   if (bl->fp_current == NULL) {
48     NORM_ERR("Failed to open file: '" FS_BRIGHTNESS_CURRENT "'.");
49   }
50 }
51 
read_backlight(struct backlight * bl)52 void read_backlight(struct backlight *bl) {
53   FILE *fp_max, *fp_current;
54   fp_max = bl->fp_max;
55   if (fp_max != NULL) {
56     rewind(fp_max);
57     fflush(fp_max);
58     if (fscanf(fp_max, "%u", &(bl->max)) < 0) {
59       NORM_ERR("Failed to read maximum brightness.");
60     }
61   } else {
62     bl->max = 0;
63   }
64   fp_current = bl->fp_current;
65   if (fp_current != NULL) {
66     rewind(fp_current);
67     fflush(fp_current);
68     if (fscanf(fp_current, "%u", &(bl->current)) < 0) {
69       NORM_ERR("Failed to read current brightness.");
70     }
71   } else {
72     bl->current = 0;
73   }
74 }
75 
get_backlight_percent(struct backlight * bl)76 unsigned get_backlight_percent(struct backlight *bl) {
77   read_backlight(bl);
78   if (bl->max == 0) {
79     return 0;
80   } else {
81     return bl->current * 100.0 / bl->max + 0.5;
82   }
83 }
84 
close_backlight(struct backlight * bl)85 void close_backlight(struct backlight *bl) {
86   if (bl->fp_max != NULL) { fclose(bl->fp_max); }
87   if (bl->fp_current != NULL) { fclose(bl->fp_current); }
88 }
89 
init_intel_backlight(struct text_object * obj)90 void init_intel_backlight(struct text_object *obj) {
91   struct backlight *bl = (struct backlight *)malloc(sizeof(struct backlight));
92   open_backlight(bl);
93   obj->data.opaque = bl;
94 }
95 
free_intel_backlight(struct text_object * obj)96 void free_intel_backlight(struct text_object *obj) {
97   struct backlight *bl = (struct backlight *)obj->data.opaque;
98   close_backlight(bl);
99   free(bl);
100 }
101 
print_intel_backlight(struct text_object * obj,char * p,unsigned int p_max_size)102 void print_intel_backlight(struct text_object *obj, char *p,
103                            unsigned int p_max_size) {
104   struct backlight *bl = (struct backlight *)obj->data.opaque;
105   unsigned percent = get_backlight_percent(bl);
106   snprintf(p, p_max_size, "%d", percent);
107 }