Skip to content
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
67 changes: 34 additions & 33 deletions brightnessctl.c
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,18 @@
# endif
#endif

#define min(a, b) ({ \
__auto_type _a = (a); \
__auto_type _b = (b); \
_a < _b ? _a : _b; })

#define max(a, b) ({ \
__auto_type _a = (a); \
__auto_type _b = (b); \
_a > _b ? _a : _b; })

#define clamp(val, lo, hi) min(max(val, lo), hi)

static char *path = "/sys/class";
static char *classes[] = { "backlight", "leds", NULL };

Expand Down Expand Up @@ -76,14 +88,12 @@ struct device {
};

enum value_type { ABSOLUTE, RELATIVE };
enum delta_type { DIRECT, DELTA };
enum sign { PLUS, MINUS };
enum delta_type { DIRECT, PLUS, MINUS };

struct value {
unsigned long val;
enum value_type v_type;
enum delta_type d_type;
enum sign sign;
};

enum operation { INFO, GET, MAX, SET, RESTORE };
Expand Down Expand Up @@ -133,7 +143,7 @@ int main(int argc, char **argv) {
int ret = 0;
int n, c, phelp = 0;
p.exponent = 1;
p.min = (struct value){ .val = 0, .v_type = ABSOLUTE, .d_type = DIRECT, .sign = PLUS };
p.min = (struct value){ .val = 0, .v_type = ABSOLUTE, .d_type = DIRECT };
while ((c = getopt_long(argc, argv, "lqpmPn::e::srhVc:d:", options, NULL)) >= 0) {
switch (c) {
case 'l':
Expand All @@ -159,10 +169,10 @@ int main(int argc, char **argv) {
break;
case 'n':
if (optarg) {
if (!parse_value(&p.min, optarg) || p.min.sign == MINUS)
if (!parse_value(&p.min, optarg) || p.min.d_type == MINUS)
fail("Invalid min-value given\n");
} else if (NULL != argv[optind] && '-' != argv[optind][0]) {
if (!parse_value(&p.min, argv[optind++]) || p.min.sign == MINUS)
if (!parse_value(&p.min, argv[optind++]) || p.min.d_type == MINUS)
fail("Invalid min-value given\n");
} else {
p.min.val = 1;
Expand Down Expand Up @@ -317,12 +327,10 @@ bool parse_value(struct value *val, char *str) {
errno = 0;
val->v_type = ABSOLUTE;
val->d_type = DIRECT;
val->sign = PLUS;
if (!str || !*str)
return false;
if (*str == '+' || *str == '-') {
val->sign = *str == '+' ? PLUS : MINUS;
val->d_type = DELTA;
val->d_type = *str == '+' ? PLUS : MINUS;
str++;
}
n = strtol(str, &buf, 10);
Expand All @@ -331,12 +339,10 @@ bool parse_value(struct value *val, char *str) {
val->val = labs(n) % LONG_MAX;
while ((c = *(buf++))) switch(c) {
case '+':
val->sign = PLUS;
val->d_type = DELTA;
val->d_type = PLUS;
break;
case '-':
val->sign = MINUS;
val->d_type = DELTA;
val->d_type = MINUS;
break;
case '%':
val->v_type = RELATIVE;
Expand Down Expand Up @@ -384,31 +390,26 @@ void print_device(struct device *dev) {
}

unsigned int calc_value(struct device *d, struct value *val) {
long new = d->curr_brightness;
if (val->d_type == DIRECT) {
new = val->v_type == ABSOLUTE ? val->val : percent_to_val(val->val, d);
goto apply;
}
long mod = val->val;
if (val->sign == MINUS)
mod *= -1;
if (val->v_type == RELATIVE) {
mod = percent_to_val(val_to_percent(d->curr_brightness, d, false) + mod, d) - d->curr_brightness;
if (val->val != 0 && mod == 0)
mod = val->sign == PLUS ? 1 : -1;
unsigned long new = val->v_type == ABSOLUTE ? d->curr_brightness :
val_to_percent(d->curr_brightness, d, false);
switch (val->d_type) {
case DIRECT:
new = val->val;
break;
case PLUS:
new = new + val->val;
break;
case MINUS:
new = new - val->val;
break;
}
new += mod;
apply:
if (val->v_type == RELATIVE)
new = percent_to_val(new, d);
if (p.min.v_type == RELATIVE) {
p.min.val = percent_to_val(p.min.val, d);
p.min.v_type = ABSOLUTE;
}
if (new < (long)p.min.val)
new = p.min.val;
if (new < 0)
new = 0;
if (new > d->max_brightness)
new = d->max_brightness;
new = clamp(new, max(p.min.val, 0UL), d->max_brightness);
return new;
}

Expand Down