Now can read from predefined restore file at /var/tmp/rexbacklight.json

This commit is contained in:
rexy712 2018-12-01 08:36:56 -08:00
parent e1b2bb8ce9
commit 904abe3294
4 changed files with 133 additions and 35 deletions

View File

@ -23,6 +23,7 @@
#define OP_DEC 2 #define OP_DEC 2
#define OP_SET 4 #define OP_SET 4
#define OP_LIST 8 #define OP_LIST 8
#define OP_RESTORE 16
#define OP_GET 128 #define OP_GET 128
#define OP_NONE 0 #define OP_NONE 0
#define OP_VERSION 254 #define OP_VERSION 254

View File

@ -29,6 +29,7 @@
#define RETVAL_MEM_ERROR 6 #define RETVAL_MEM_ERROR 6
#define RETVAL_INTERNAL_ERROR 7 #define RETVAL_INTERNAL_ERROR 7
#define RETVAL_SUCCESS EXIT_SUCCESS #define RETVAL_SUCCESS EXIT_SUCCESS
extern int return_value; extern int return_value;
void mem_error(void); void mem_error(void);

View File

@ -54,6 +54,9 @@
#define DEC_LONG_OPT NO_OPT #define DEC_LONG_OPT NO_OPT
#define DEC_SHORT_OPT NO_OPT #define DEC_SHORT_OPT NO_OPT
#define DEC_XBACK_OPT "-dec" #define DEC_XBACK_OPT "-dec"
#define RESTORE_LONG_OPT "--restore"
#define RESTORE_SHORT_OPT "-R"
#define RESTORE_XBACK_OPT NO_OPT
#define DEVICE_DESC "select which device to control" #define DEVICE_DESC "select which device to control"
#define FADE_DESC "change brightness over time interval" #define FADE_DESC "change brightness over time interval"
@ -65,6 +68,7 @@
#define SET_DESC "set backlight device to specified value" #define SET_DESC "set backlight device to specified value"
#define INC_DESC "increase backlight device by specified value" #define INC_DESC "increase backlight device by specified value"
#define DEC_DESC "decrease backlight device by specified value" #define DEC_DESC "decrease backlight device by specified value"
#define RESTORE_DESC "reassign previously saved backlight values"
int strcmp_handle_null(const char* one, const char* two){ int strcmp_handle_null(const char* one, const char* two){
if(!one) if(!one)
@ -82,28 +86,31 @@ int strcmp_handle_null(const char* one, const char* two){
#define CHECK_OPTION(opt, arg) (!strcmp_handle_null(opt##_LONG_OPT, arg) || !strcmp_handle_null(opt##_SHORT_OPT, arg) || !strcmp_handle_null(opt##_XBACK_OPT, arg)) #define CHECK_OPTION(opt, arg) (!strcmp_handle_null(opt##_LONG_OPT, arg) || !strcmp_handle_null(opt##_SHORT_OPT, arg) || !strcmp_handle_null(opt##_XBACK_OPT, arg))
struct cmd_arg rexbacklight_args[] = { struct cmd_arg rexbacklight_args[] = {
{DEVICE_LONG_OPT, DEVICE_SHORT_OPT, DEVICE_XBACK_OPT, DEVICE_DESC}, {DEVICE_LONG_OPT, DEVICE_SHORT_OPT, DEVICE_XBACK_OPT, DEVICE_DESC},
{NO_OPT, NO_OPT, SET_XBACK_OPT, SET_DESC}, {NO_OPT, NO_OPT, SET_XBACK_OPT, SET_DESC},
{NO_OPT, NO_OPT, INC_XBACK_OPT, INC_DESC}, {NO_OPT, NO_OPT, INC_XBACK_OPT, INC_DESC},
{NO_OPT, NO_OPT, DEC_XBACK_OPT, DEC_DESC}, {NO_OPT, NO_OPT, DEC_XBACK_OPT, DEC_DESC},
{FADE_LONG_OPT, FADE_SHORT_OPT, FADE_XBACK_OPT, FADE_DESC}, {FADE_LONG_OPT, FADE_SHORT_OPT, FADE_XBACK_OPT, FADE_DESC},
{STEPS_LONG_OPT, STEPS_SHORT_OPT, STEPS_XBACK_OPT, STEPS_DESC}, {STEPS_LONG_OPT, STEPS_SHORT_OPT, STEPS_XBACK_OPT, STEPS_DESC},
{GET_LONG_OPT, GET_SHORT_OPT, GET_XBACK_OPT, GET_DESC}, {GET_LONG_OPT, GET_SHORT_OPT, GET_XBACK_OPT, GET_DESC},
{HELP_LONG_OPT, HELP_SHORT_OPT, HELP_XBACK_OPT, HELP_DESC}, {LIST_LONG_OPT, LIST_SHORT_OPT, LIST_XBACK_OPT, LIST_DESC},
{VERSION_LONG_OPT, NO_OPT, VERSION_XBACK_OPT, VERSION_DESC} {RESTORE_LONG_OPT, RESTORE_SHORT_OPT, RESTORE_XBACK_OPT, RESTORE_DESC},
{HELP_LONG_OPT, HELP_SHORT_OPT, HELP_XBACK_OPT, HELP_DESC},
{VERSION_LONG_OPT, NO_OPT, VERSION_XBACK_OPT, VERSION_DESC}
}; };
#else //XBACKLIGHT_COMPAT_OPTIONS #else //XBACKLIGHT_COMPAT_OPTIONS
#define CHECK_OPTION(opt, arg) (!strcmp_handle_null(opt##_LONG_OPT, arg) || !strcmp_handle_null(opt##_SHORT_OPT, arg)) #define CHECK_OPTION(opt, arg) (!strcmp_handle_null(opt##_LONG_OPT, arg) || !strcmp_handle_null(opt##_SHORT_OPT, arg))
struct cmd_arg rexbacklight_args[] = { struct cmd_arg rexbacklight_args[] = {
{DEVICE_LONG_OPT, DEVICE_SHORT_OPT, DEVICE_DESC}, {DEVICE_LONG_OPT, DEVICE_SHORT_OPT, DEVICE_DESC},
{FADE_LONG_OPT, FADE_SHORT_OPT, FADE_DESC}, {FADE_LONG_OPT, FADE_SHORT_OPT, FADE_DESC},
{STEPS_LONG_OPT, STEPS_SHORT_OPT, STEPS_DESC}, {STEPS_LONG_OPT, STEPS_SHORT_OPT, STEPS_DESC},
{GET_LONG_OPT, GET_SHORT_OPT, GET_DESC}, {GET_LONG_OPT, GET_SHORT_OPT, GET_DESC},
{LIST_LONG_OPT, LIST_SHORT_OPT, LIST_DESC}, {LIST_LONG_OPT, LIST_SHORT_OPT, LIST_DESC},
{HELP_LONG_OPT, HELP_SHORT_OPT, HELP_DESC}, {RESTORE_LONG_OPT, RESTORE_SHORT_OPT, RESTORE_DESC},
{VERSION_LONG_OPT, NO_OPT, VERSION_DESC} {HELP_LONG_OPT, HELP_SHORT_OPT, HELP_DESC},
{VERSION_LONG_OPT, NO_OPT, VERSION_DESC}
}; };
#endif //XBACKLIGHT_COMPAT_OPTIONS #endif //XBACKLIGHT_COMPAT_OPTIONS
@ -195,6 +202,9 @@ struct arg_values process_cmd_args(int argc, char** argv){
ret.next = NULL; ret.next = NULL;
return ret; return ret;
} }
else if(CHECK_OPTION(RESTORE, argv[i])){
ret.operation = OP_RESTORE;
}
else if(!strcmp(argv[i], "max")){ else if(!strcmp(argv[i], "max")){
curr->operation = OP_SET; curr->operation = OP_SET;
curr->delta = 100; curr->delta = 100;

View File

@ -26,6 +26,7 @@
#include <dirent.h> #include <dirent.h>
#include <sys/time.h> #include <sys/time.h>
#include <time.h> #include <time.h>
#include <rjp.h>
#include "common.h" #include "common.h"
#include "cmd.h" #include "cmd.h"
@ -36,10 +37,12 @@
//This is where backlight devices can be found in sysfs //This is where backlight devices can be found in sysfs
static const char* device_dir = "/sys/class/backlight/"; static const char* device_dir = "/sys/class/backlight/";
const char* executable_name = "rexbacklight"; const char* executable_name = "rexbacklight";
static const char* restore_file = "/var/tmp/rexbacklight.json";
#elif defined(REXLEDCTL) #elif defined(REXLEDCTL)
//This is where led devices can be found in sysfs //This is where led devices can be found in sysfs
static const char* device_dir = "/sys/class/leds"; static const char* device_dir = "/sys/class/leds";
const char* executable_name = "rexledctl"; const char* executable_name = "rexledctl";
static const char* restore_file = "/var/tmp/rexledctl.json";
#else #else
#error "UNDEFINED PROGRAM NAME!" #error "UNDEFINED PROGRAM NAME!"
#endif #endif
@ -62,10 +65,10 @@ void io_error(const char* error, const char* type, const char* name){
fprintf(stderr, "Unable to %s %s '%s'!\n", error, type, name); fprintf(stderr, "Unable to %s %s '%s'!\n", error, type, name);
} }
void io_error_2(const char* error, const char* type, const char* name, const char* name2){ void io_error_2(const char* error, const char* type, const char* name, const char* name2){
fprintf(stderr, "Unable to %s %s '%s/%s'!\n", error, type, name, name2); fprintf(stderr, "Unable to %s %s '%s%s'!\n", error, type, name, name2);
} }
void io_error_3(const char* error, const char* type, const char* name, const char* name2, const char* name3){ void io_error_3(const char* error, const char* type, const char* name, const char* name2, const char* name3){
fprintf(stderr, "Unable to %s %s '%s/%s/%s'!\n", error, type, name, name2, name3); fprintf(stderr, "Unable to %s %s '%s%s%s'!\n", error, type, name, name2, name3);
} }
//Clean up a string array //Clean up a string array
@ -235,31 +238,108 @@ void do_list(struct string_array* names){
fprintf(stdout, "%s\n", names->list[i]); fprintf(stdout, "%s\n", names->list[i]);
} }
RJP_value* read_restore_file(const char* file){
size_t filesize;
char* file_contents;
int i;
FILE* fp = fopen(file, "r");
if(!fp){
fprintf(stderr, "Could not restore! No restore file found!\n");
return NULL;
}
fseek(fp, 0, SEEK_END);
filesize = ftell(fp);
fseek(fp, 0, SEEK_SET);
file_contents = malloc(filesize+1);
i = fread(file_contents, filesize, 1, fp);
fclose(fp);
file_contents[filesize] = 0;
RJP_value* root = rjp_parse(file_contents);
free(file_contents);
return root;
}
int individual_device_op(struct arg_values* curr){
if(chdir(curr->device)){
io_error_2(IO_ERROR_OPEN, IO_ERROR_DIR, device_dir, curr->device);
return RETVAL_INVALID_DIR;
}
switch(curr->operation){
case OP_SET:
case OP_INC:
case OP_DEC:
do_assignment(curr, curr->device);
break;
case OP_GET:
do_get(curr->device);
break;
}
if(chdir(device_dir)){
io_error(IO_ERROR_OPEN, IO_ERROR_DIR, device_dir);
return RETVAL_INTERNAL_ERROR;
}
return return_value;
}
RJP_value* find_matching_json_device(const char* name, RJP_value* root){
for(RJP_value* curr = rjp_get_member(root);curr;curr = rjp_next_member(curr)){
if(!strcmp(rjp_member_name(curr), name)){
return curr;
}
}
return NULL;
}
int prep_restore(struct arg_values* curr, RJP_value** root, int* try_restore){
if(!*root && *try_restore){
*root = read_restore_file(restore_file);
if(!*root){
*try_restore = 0;
return 0;
}
}
RJP_value* match = find_matching_json_device(curr->device, *root);
if(!match){
fprintf(stderr, "No matching device '%s' in restore file!\n", curr->device);
return 0;
}
curr->operation = OP_SET;
curr->delta = rjp_value_dfloat(match);
return 1;
}
//If devices were specified, this function will run //If devices were specified, this function will run
void individual_device_loop(struct arg_values* a){ void individual_device_loop(struct arg_values* a){
struct arg_values* curr; struct arg_values* curr;
RJP_value* root = 0;
int try_restore = 1;
for(curr = a->next;curr;curr = curr->next){ for(curr = a->next;curr;curr = curr->next){
if(chdir(curr->device)){ if(curr->operation == OP_RESTORE){
io_error_2(IO_ERROR_OPEN, IO_ERROR_DIR, device_dir, curr->device); if(!prep_restore(curr, &root, &try_restore))
return_value = RETVAL_INVALID_DIR; continue;
continue;
} }
switch(curr->operation){ return_value = individual_device_op(curr);
case OP_SET: if(return_value == RETVAL_INTERNAL_ERROR){
case OP_INC: rjp_free(root);
case OP_DEC:
do_assignment(curr, curr->device);
break;
case OP_GET:
do_get(curr->device);
break;
}
if(chdir(device_dir)){
io_error(IO_ERROR_OPEN, IO_ERROR_DIR, device_dir);
return_value = RETVAL_INVALID_DIR;
return; return;
} }
} }
rjp_free(root);
}
void process_restore_file(void){
RJP_value* root = read_restore_file(restore_file);
if(!root)
return;
struct arg_values tmp = {.next = NULL,
.fade_duration = 0,
.fade_steps = 1,
.operation = OP_SET};
for(RJP_value* curr = rjp_get_member(root);curr;curr = rjp_next_member(curr)){
tmp.device = rjp_member_name(curr);
tmp.delta = rjp_value_dfloat(curr);
individual_device_op(&tmp);
}
rjp_free(root);
} }
//If no devices were specified, this function will run //If no devices were specified, this function will run
@ -301,6 +381,12 @@ void all_device_loop(struct string_array* device_names, struct arg_values* args)
} }
} }
break; break;
case OP_RESTORE:;
process_restore_file();
break;
default:
fprintf(stderr, "Internal processing error!\n");
break;
} }
} }