Options to check if file exists on calculator

This commit is contained in:
Empathic Qubit 2023-01-07 13:18:50 +01:00
parent 310280ae71
commit c2239d3ff7
3 changed files with 201 additions and 83 deletions

View file

@ -33,7 +33,9 @@
"system_error": "cpp",
"tuple": "cpp",
"typeinfo": "cpp",
"cstddef": "c"
"cstddef": "c",
"keys83p.h": "c",
"stdlib.h": "c"
},
"cmake.configureOnOpen": true
}

View file

@ -6,6 +6,11 @@
#include <stdlib.h>
#include <string.h>
#ifndef EXIT_FAILURE
#define EXIT_FAILURE 1
#define EXIT_SUCCESS 0
#endif
typedef enum {
LEVEL_ERROR,
LEVEL_WARN,

View file

@ -18,17 +18,120 @@
static char *subtype = "";
static char *program = "";
static CalcModel model = CALC_TI83P;
static char *model_requested = "";
static char *keys = "";
static int reset_ram = 0;
static int reset_archive_vars = 0;
static char *exists_filename = "";
static char *exists_type = "";
static int exists_version = -1;
static int exists_size = -1;
void show_help() {
log(LEVEL_INFO,
"Syntax: tikeys [options]\n"
"\n"
"Options:\n"
"[-m|--model=83p] choose the connected model. Default: 83p\n"
"[-r|--reset-ram] reset the RAM (83p and variants)\n"
"[-a|--reset-archive-vars] reset the archive vars (83p and variants)\n"
"[-k|--keys=AZ09]] press alphanumeric keys\n"
"[[-s|--subtype=noshell] -p|--program=PROGNAME]\n"
"\n"
"[-e|--exists=FILENAME return success if the file exists on the calculator\n"
" [-t|--type=PGRM] return success only if the type matches\n"
" [-v|--version=1] return success only if the file version matches\n"
" [-z|--size=1] return success only if the file size matches\n"
"]\n"
);
}
int get_args(int argc, char *argv[]) {
const struct option long_opts[] = {
{"calc", required_argument, 0, 'c'},
{"reset-ram", no_argument, &reset_ram, 1},
{"reset-archive-vars", no_argument, &reset_archive_vars, 1},
{"keys", required_argument, 0, 'k'},
{"subtype", required_argument, 0, 's'},
{"program", required_argument, 0, 'p'},
{"exists", required_argument, 0, 'e'},
{"type", required_argument, 0, 't'},
{"version", required_argument, 0, 'v'},
{"size", required_argument, 0, 'z'},
{"help", no_argument, 0, 'h'},
{0,0,0,0}
};
optind = 0;
int opt_index = 0;
int opt;
while((opt = getopt_long(argc, argv, ":c:rak:s:p:e:t:v:z:h", long_opts, &opt_index)) != -1) {
if(optarg != NULL && strncmp(optarg, "=", 1) == 0) {
optarg = &optarg[1];
}
if(opt == 0 && long_opts[opt_index].flag) {
// Do nothing
}
else if(optarg != NULL && (strncmp(optarg, "-", 1) == 0)) {
log(LEVEL_ERROR, "Argument for -%c started with a -: %s\n", opt, optarg);
show_help();
return EXIT_FAILURE;
}
else if(opt == ':') {
log(LEVEL_ERROR, "-%s requires an argument\n", optarg);
show_help();
return EXIT_FAILURE;
}
else if(opt == 's') {
subtype = optarg;
}
else if(opt == 'p') {
program = optarg;
}
else if(opt == 'k') {
keys = optarg;
}
else if(opt == 'r') {
reset_ram = 1;
}
else if(opt == 'a') {
reset_archive_vars = 1;
}
else if(opt == 'e') {
exists_filename = optarg;
}
else if(opt == 't') {
exists_type = optarg;
}
else if(opt == 'v') {
sscanf(optarg, "%d", &exists_version);
}
else if(opt == 'z') {
sscanf(optarg, "%d", &exists_size);
}
else if(opt == 'c') {
model_requested = optarg;
}
else if(opt == 'h') {
show_help();
return EXIT_FAILURE;
}
}
return EXIT_SUCCESS;
}
static CalcHandle *calc_handle = NULL;
static CableHandle *cable_handle = NULL;
static CalcModel model = CALC_TI83P;
void show_help() {
log(LEVEL_INFO, "Syntax: tikeys [-m|--model=83p] [-r|--reset-ram] [-k|--keys=AZ09] [[-s|--subtype=noshell] -p|--program=PROGNAME]\n");
}
static const CalcKey* (*keys_func)(uint8_t ascii_code) = NULL;
void cleanup() {
if(calc_handle) {
@ -136,7 +239,7 @@ int start_app(GNode *apps, char *app_name, bool is_program) {
if(is_program || !is_ti8x) {
VarEntry *app = get_program(apps, app_name);
if(app == NULL) {
return 1;
return EXIT_FAILURE;
}
if(is_ti8x && strcmp(tifiles_vartype2string(model, app->type), "PPRGM") == 0) {
@ -147,12 +250,12 @@ int start_app(GNode *apps, char *app_name, bool is_program) {
ticalcs_calc_execute(calc_handle, app, "");
return 0;
return EXIT_SUCCESS;
}
int app_idx = get_program_index(apps, app_name);
if(app_idx == -1) {
return 1;
return EXIT_FAILURE;
}
if(is_program) {
@ -162,7 +265,7 @@ int start_app(GNode *apps, char *app_name, bool is_program) {
send_key(KEY83P_AppsMenu, 1);
}
send_key(ticalcs_keys_83p(app_name[0])->normal.value, 1);
send_key(keys_func(app_name[0])->normal.value, 1);
for(int i = 0; i < app_idx; i++) {
send_key(KEY83P_Down, 1);
@ -173,7 +276,7 @@ int start_app(GNode *apps, char *app_name, bool is_program) {
send_key(KEY83P_Enter, 0);
}
return 0;
return EXIT_SUCCESS;
}
@ -188,60 +291,10 @@ int main(int argc, char *argv[]) {
utils_parse_args(argc, argv);
const struct option long_opts[] = {
{"calc", required_argument, 0, 'c'},
{"reset-ram", no_argument, &reset_ram, 1},
{"keys", required_argument, 0, 'k'},
{"subtype", required_argument, 0, 's'},
{"program", required_argument, 0, 'p'},
{"help", no_argument, 0, 'h'},
{0,0,0,0}
};
optind = 0;
int opt_index = 0;
int opt;
while((opt = getopt_long(argc, argv, ":c:rt:k:s:p:h", long_opts, &opt_index)) != -1) {
if(optarg != NULL && strncmp(optarg, "=", 1) == 0) {
optarg = &optarg[1];
}
if(opt == 0 && long_opts[opt_index].flag) {
// Do nothing
}
else if(optarg != NULL && (strncmp(optarg, "-", 1) == 0)) {
log(LEVEL_ERROR, "Argument for -%c started with a -: %s\n", opt, optarg);
show_help();
int err;
if((err = get_args(argc, argv))) {
cleanup();
return 1;
}
else if(opt == ':') {
log(LEVEL_ERROR, "-%s requires an argument\n", optarg);
show_help();
cleanup();
return 1;
}
else if(opt == 's') {
subtype = optarg;
}
else if(opt == 'p') {
program = optarg;
}
else if(opt == 'k') {
keys = optarg;
}
else if(opt == 'r') {
reset_ram = 1;
}
else if(opt == 'c') {
model_requested = optarg;
}
else if(opt == 'h') {
show_help();
cleanup();
return 0;
}
return EXIT_FAILURE;
}
log(LEVEL_TRACE, "Subtype: %s\n", subtype);
@ -254,25 +307,28 @@ int main(int argc, char *argv[]) {
if(model == CALC_NONE) {
log(LEVEL_ERROR, "Invalid calculator model\n");
cleanup();
return 1;
return EXIT_FAILURE;
}
}
int err;
if(model == CALC_TI83P) {
keys_func = &ticalcs_keys_83p;
}
ticables_library_init();
cable_handle = utils_setup_cable();
if(cable_handle == NULL) {
log(LEVEL_ERROR, "Cable not found!\n");
cleanup();
return 1;
return EXIT_FAILURE;
}
err = ticables_cable_open(cable_handle);
if(err) {
log(LEVEL_ERROR, "Could not open cable: %d\n", err);
cleanup();
return 1;
return EXIT_FAILURE;
}
CableDeviceInfo info;
@ -280,14 +336,14 @@ int main(int argc, char *argv[]) {
if(err) {
log(LEVEL_ERROR, "Could not read device info: %d\n", err);
cleanup();
return 1;
return EXIT_FAILURE;
}
err = ticables_cable_close(cable_handle);
if(err) {
log(LEVEL_ERROR, "Could not close cable: %d\n", err);
cleanup();
return 1;
return EXIT_FAILURE;
}
ticables_handle_del(cable_handle);
@ -307,13 +363,68 @@ int main(int argc, char *argv[]) {
send_key(KEY83P_ResetMem, 0);
}
if(reset_archive_vars) {
send_key(KEY83P_Quit, 1);
send_key(KEY83P_Clear, 1);
log(LEVEL_WARN, "Resetting archive vars...\n");
send_key(KEY83P_Mem, 1);
send_key(keys_func('7')->normal.value, 1);
send_key(KEY83P_Right, 1);
send_key(keys_func('1')->normal.value, 1);
send_key(keys_func('2')->normal.value, 0);
}
if(strlen(keys) > 0) {
for(int i = 0; i < strlen(keys); i++) {
send_key(ticalcs_keys_83p(keys[i])->normal.value, 1);
send_key(keys_func(keys[i])->normal.value, 1);
}
}
if(strlen(subtype) > 0 || strlen(program) > 0) {
if(strlen(exists_filename) > 0) {
log(LEVEL_INFO, "Checking for existence of file %s", exists_filename);
GNode *lists[2];
while((err = ticalcs_calc_get_dirlist(calc_handle, &lists[0], &lists[1])));
for (int l = 0; l < sizeof(lists) / sizeof(lists[0]); l++) {
for (int i = 0; i < (int)g_node_n_children(lists[l]); i++) {
GNode *parent = g_node_nth_child(lists[l], i);
VarEntry *ve = parent->data;
for (int j = 0; j < (int)g_node_n_children(parent); j++) {
GNode *child = g_node_nth_child(parent, j);
ve = child->data;
if(ve != NULL && strcmp(ve->name, exists_filename) == 0) {
log(LEVEL_INFO, "Found file: %s\n", exists_filename);
if(exists_version >= 0 && ve->version != exists_version) {
log(LEVEL_WARN, "Version didn't match: %d\n", ve->version);
continue;
}
if(exists_size >= 0 && ve->size != exists_size) {
log(LEVEL_WARN, "Size didn't match: %d\n", ve->size);
continue;
}
const char* str_type = tifiles_vartype2string(model, ve->type);
if(strlen(exists_type) > 0 && strcmp(exists_type, str_type) != 0) {
log(LEVEL_WARN, "Type didn't match: %s\n", str_type);
continue;
}
cleanup();
return EXIT_SUCCESS;
}
}
}
}
log(LEVEL_ERROR, "File not found: %s\n", exists_filename);
cleanup();
return EXIT_FAILURE;
}
else if(strlen(subtype) > 0 || strlen(program) > 0) {
log(LEVEL_DEBUG, "Got a program startup request.\n");
send_key(KEY83P_Quit, 1);
@ -322,17 +433,17 @@ int main(int argc, char *argv[]) {
if(strcmp(subtype, "asm") == 0) {
log(LEVEL_ERROR, "asm is not supported! Start it manually!\n");
cleanup();
return 1;
return EXIT_FAILURE;
}
else if(strcmp(subtype, "tse") == 0) {
log(LEVEL_ERROR, "tse is not supported! Start it manually!\n");
cleanup();
return 1;
return EXIT_FAILURE;
}
else if(strcmp(subtype, "ion") == 0) {
log(LEVEL_WARN, "ion will be started, but you still need to start the program yourself.\n");
send_key(KEY83P_Prgm, 1);
send_key(ticalcs_keys_83p('A')->normal.value, 1);
send_key(keys_func('A')->normal.value, 1);
send_key(KEY83P_Enter, 1);
send_key(KEY83P_Enter, 0);
}
@ -347,7 +458,7 @@ int main(int argc, char *argv[]) {
if((err = start_app(apps, "MirageOS", 0))) {
log(LEVEL_ERROR, "Could not start MirageOS. Is it installed?\n");
cleanup();
return 1;
return EXIT_FAILURE;
}
}
else if(strlen(program) > 0) {
@ -363,7 +474,7 @@ int main(int argc, char *argv[]) {
if(get_program(vars, program) == NULL) {
log(LEVEL_ERROR, "Could not find %s. Is it installed? Error %d\n", program, err);
cleanup();
return 1;
return EXIT_FAILURE;
}
log(LEVEL_INFO, "Verifying that noshell is correctly hooked.\n");
@ -371,19 +482,19 @@ int main(int argc, char *argv[]) {
if((err = start_app(apps, "Noshell ", 0))) {
log(LEVEL_ERROR, "Could not start Noshell. Is it installed?\n");
cleanup();
return 1;
return EXIT_FAILURE;
}
ticables_options_set_timeout(cable_handle, CABLE_FAST_TIMEOUT);
send_key(ticalcs_keys_83p('1')->normal.value, 0);
send_key(keys_func('1')->normal.value, 0);
send_key(KEY83P_Enter, 0);
send_key(ticalcs_keys_83p('6')->normal.value, 0);
send_key(keys_func('6')->normal.value, 0);
ticables_options_set_timeout(cable_handle, CABLE_TIMEOUT);
if((err = start_app(vars, program, 1))) {
log(LEVEL_ERROR, "Could not start %s. Is it installed? Error %d\n", program, err);
cleanup();
return 1;
return EXIT_FAILURE;
}
log(LEVEL_INFO, "Finished sucessfully!\n");
@ -391,5 +502,5 @@ int main(int argc, char *argv[]) {
}
cleanup();
return 0;
return EXIT_SUCCESS;
}