opensc-explorer: convert do_info() to using tables
* use ID<->name tables instead of arrays of strings where the index was treated like some "magic" constant. With the new mapping tables, the meaning is obvious. * fix a bug with ac_ops_df[]: before the conversion, it was a list of pointers to strings but was in one case treated like it was a mapping table. With the conversion to a mapping table, and the adaption of other code parts this bug got fixed "automagically" ;-) * use common code to cleanly print ACLs for DFs & EFs * harmonize EF structure names to the ones used in ISO 7816-4 Signed-off-by: Peter Marschall <peter@adpm.de>
This commit is contained in:
parent
9863072845
commit
78838812fb
|
@ -37,6 +37,12 @@
|
||||||
|
|
||||||
#define DIM(v) (sizeof(v)/sizeof((v)[0]))
|
#define DIM(v) (sizeof(v)/sizeof((v)[0]))
|
||||||
|
|
||||||
|
/* type for associations of IDs to names */
|
||||||
|
typedef struct _id2str {
|
||||||
|
unsigned int id;
|
||||||
|
const char *str;
|
||||||
|
} id2str_t;
|
||||||
|
|
||||||
static const char *app_name = "opensc-explorer";
|
static const char *app_name = "opensc-explorer";
|
||||||
|
|
||||||
static int opt_wait = 0, verbose = 0;
|
static int opt_wait = 0, verbose = 0;
|
||||||
|
@ -432,6 +438,7 @@ static int do_info(int argc, char **argv)
|
||||||
size_t i;
|
size_t i;
|
||||||
const char *st;
|
const char *st;
|
||||||
int r, not_current = 1;
|
int r, not_current = 1;
|
||||||
|
const id2str_t *ac_ops = NULL;
|
||||||
|
|
||||||
if (!argc) {
|
if (!argc) {
|
||||||
path = current_path;
|
path = current_path;
|
||||||
|
@ -472,48 +479,67 @@ static int do_info(int argc, char **argv)
|
||||||
printf("\n%-15s%lu bytes\n", "File size:", (unsigned long) file->size);
|
printf("\n%-15s%lu bytes\n", "File size:", (unsigned long) file->size);
|
||||||
|
|
||||||
if (file->type == SC_FILE_TYPE_DF) {
|
if (file->type == SC_FILE_TYPE_DF) {
|
||||||
const char *ops[] = {
|
static const id2str_t ac_ops_df[] = {
|
||||||
"SELECT", "LOCK", "DELETE", "CREATE", "REHABILITATE",
|
{ SC_AC_OP_SELECT, "SELECT" },
|
||||||
"INVALIDATE", "LIST FILES", "CRYPTO", "DELETE SELF"
|
{ SC_AC_OP_LOCK, "LOCK" },
|
||||||
|
{ SC_AC_OP_DELETE, "DELETE" },
|
||||||
|
{ SC_AC_OP_CREATE, "CREATE" },
|
||||||
|
{ SC_AC_OP_REHABILITATE, "REHABILITATE" },
|
||||||
|
{ SC_AC_OP_INVALIDATE, "INVALIDATE" },
|
||||||
|
{ SC_AC_OP_LIST_FILES, "LIST FILES" },
|
||||||
|
{ SC_AC_OP_CRYPTO, "CRYPTO" },
|
||||||
|
{ SC_AC_OP_DELETE_SELF, "DELETE SELF" },
|
||||||
|
{ 0, NULL }
|
||||||
};
|
};
|
||||||
|
|
||||||
if (file->namelen) {
|
if (file->namelen) {
|
||||||
printf("%-15s", "DF name:");
|
printf("%-15s", "DF name:");
|
||||||
util_print_binary(stdout, file->name, file->namelen);
|
util_print_binary(stdout, file->name, file->namelen);
|
||||||
printf("\n");
|
printf("\n");
|
||||||
}
|
}
|
||||||
for (i = 0; i < sizeof(ops)/sizeof(ops[0]); i++) {
|
|
||||||
char buf[80];
|
|
||||||
|
|
||||||
sprintf(buf, "ACL for %s:", ops[i]);
|
ac_ops = ac_ops_df;
|
||||||
printf("%-25s%s\n", buf, util_acl_to_str(sc_file_get_acl_entry(file, i)));
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
const char *structs[] = {
|
static const id2str_t ac_ops_ef[] = {
|
||||||
"Unknown", "Transparent", "Linear fixed",
|
{ SC_AC_OP_READ, "READ" },
|
||||||
"Linear fixed, SIMPLE-TLV", "Linear variable",
|
{ SC_AC_OP_UPDATE, "UPDATE" },
|
||||||
"Linear variable TLV", "Cyclic, SIMPLE-TLV",
|
{ SC_AC_OP_DELETE, "DELETE" },
|
||||||
|
{ SC_AC_OP_WRITE, "WRITE" },
|
||||||
|
{ SC_AC_OP_REHABILITATE, "REHABILITATE" },
|
||||||
|
{ SC_AC_OP_INVALIDATE, "INVALIDATE" },
|
||||||
|
{ SC_AC_OP_LIST_FILES, "LIST FILES" },
|
||||||
|
{ SC_AC_OP_CRYPTO, "CRYPTO" },
|
||||||
|
{ 0, NULL }
|
||||||
};
|
};
|
||||||
const struct {
|
const id2str_t ef_type_name[] = {
|
||||||
const char * label;
|
{ SC_FILE_EF_TRANSPARENT, "Transparent" },
|
||||||
int op;
|
{ SC_FILE_EF_LINEAR_FIXED, "Linear fixed" },
|
||||||
} ops[] = {
|
{ SC_FILE_EF_LINEAR_FIXED_TLV, "Linear fixed, SIMPLE-TLV" },
|
||||||
{ "READ", SC_AC_OP_READ },
|
{ SC_FILE_EF_LINEAR_VARIABLE, "Linear variable" },
|
||||||
{ "UPDATE", SC_AC_OP_UPDATE },
|
{ SC_FILE_EF_LINEAR_VARIABLE_TLV, "Linear variable, SIMPLE-TLV" },
|
||||||
{ "DELETE", SC_AC_OP_DELETE },
|
{ SC_FILE_EF_CYCLIC, "Cyclic" },
|
||||||
{ "WRITE", SC_AC_OP_WRITE },
|
{ SC_FILE_EF_CYCLIC_TLV, "Cyclic, SIMPLE-TLV" },
|
||||||
{ "REHABILITATE", SC_AC_OP_REHABILITATE },
|
{ 0, NULL }
|
||||||
{ "INVALIDATE", SC_AC_OP_INVALIDATE },
|
|
||||||
{ "LIST_FILES", SC_AC_OP_LIST_FILES },
|
|
||||||
{ "CRYPTO", SC_AC_OP_CRYPTO },
|
|
||||||
};
|
};
|
||||||
printf("%-15s%s\n", "EF structure:", structs[file->ef_structure]);
|
const char *ef_type = "Unknown";
|
||||||
for (i = 0; i < sizeof(ops)/sizeof(ops[0]); i++) {
|
|
||||||
char buf[80];
|
|
||||||
|
|
||||||
sprintf(buf, "ACL for %s:", ops[i].label);
|
for (i = 0; ef_type_name[i].str != NULL; i++)
|
||||||
printf("%-25s%s\n", buf, util_acl_to_str(sc_file_get_acl_entry(file, ops[i].op)));
|
if (file->ef_structure == ef_type_name[i].id)
|
||||||
}
|
ef_type = ef_type_name[i].str;
|
||||||
|
printf("%-15s%s\n", "EF structure:", ef_type);
|
||||||
|
|
||||||
|
ac_ops = ac_ops_ef;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (i = 0; ac_ops != NULL && ac_ops[i].str != NULL; i++) {
|
||||||
|
int len = strlen(ac_ops[i].str);
|
||||||
|
|
||||||
|
printf("ACL for %s:%*s %s\n",
|
||||||
|
ac_ops[i].str,
|
||||||
|
(12 > len) ? (12 - len) : 0, "",
|
||||||
|
util_acl_to_str(sc_file_get_acl_entry(file, ac_ops[i].id)));
|
||||||
|
}
|
||||||
|
|
||||||
if (file->prop_attr_len) {
|
if (file->prop_attr_len) {
|
||||||
printf("%-25s", "Proprietary attributes:");
|
printf("%-25s", "Proprietary attributes:");
|
||||||
for (i = 0; i < file->prop_attr_len; i++)
|
for (i = 0; i < file->prop_attr_len; i++)
|
||||||
|
|
Loading…
Reference in New Issue