#if defined(CONFIG_PROC_FS) #include #include #include #include #include #include #include #include #include #include #include #include #include #include "avm_sbl.h" #if defined(CONFIG_OF_AVM_DT) #include #endif static struct sbl_boot_status * get_sbl_boot_status(void){ #if defined(CONFIG_OF_AVM_DT) struct sbl_boot_status * sbl_status; struct reserved_mem *rmem; rmem = fdt_get_reserved_mem_resource("avm_sbl_boot_string"); if(rmem){ sbl_status = (struct sbl_boot_status * ) phys_to_virt(rmem->base); return sbl_status; } #endif pr_info("[%s] No reserved memory for entry for avm_sbl_boot_string\n", __FUNCTION__); return 0; } static struct proc_dir_entry *sblprocdir; static struct sbl_boot_status * sbl_status; static int sbl_magic_match(void){ if(sbl_status == NULL){ return 0; } if(!strcmp(sbl_status->magic_str, SBL_MAGIC_STRING)){ return 1; } return 0; } static void proc_tz_boot_index(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d\n", sbl_status->tz_boot_index); } static void proc_eva_boot_index(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d\n", sbl_status->eva_boot_index); } static void proc_tz_boot_ack(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d\n", sbl_status->tz_boot_successful); } static void proc_eva_boot_ack(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d\n", sbl_status->eva_boot_successful); } static int proc_write_eva_boot_ack(char *buffer, void *priv __maybe_unused){ int ack = 0; if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); return -ENOENT; } sscanf(buffer, "%d", &ack); if((ack == 1) || (ack == 0)){ sbl_status->eva_boot_successful = ack; return 0; } return -EBADMSG; } static int proc_write_tz_boot_ack(char *buffer, void *priv __maybe_unused){ int ack = 0; if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); return -ENOENT; } sscanf(buffer, "%d", &ack); if((ack == 1) || (ack == 0)){ sbl_status->tz_boot_successful = ack; return 0; } return -EBADMSG; } static void proc_eva0_verified(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d\n", sbl_status->eva_verified[0]); } static void proc_eva1_verified(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d\n", sbl_status->eva_verified[1]); } static void proc_tz0_verified(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d\n", sbl_status->tz_verified[0]); } static void proc_tz1_verified(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d\n", sbl_status->tz_verified[1]); } static void proc_eva0_version(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d%s\n", sbl_status->eva_version[0], (sbl_status->eva_modified[0] ? "M" : "")); } static void proc_eva1_version(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d%s\n", sbl_status->eva_version[1], (sbl_status->eva_modified[1] ? "M" : "")); } static void proc_tz0_version(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d%s\n", sbl_status->tz_version[0], (sbl_status->tz_modified[0] ? "M" : "")); } static void proc_tz1_version(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d%s\n", sbl_status->tz_version[1], (sbl_status->tz_modified[1] ? "M" : "")); } static void proc_sbl_version(struct seq_file *seq, void *priv __maybe_unused){ if(sbl_magic_match() == 0){ pr_err("[%s] Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); seq_printf(seq, "Magic mismatch"); return; } seq_printf(seq, "%d%s\n", sbl_status->sbl_version, (sbl_status->sbl_modified ? "M" : "")); } static __init int proc_sbl_boot_status(void) { sbl_status = get_sbl_boot_status(); if(sbl_status == NULL){ return 0; } if(sbl_magic_match() == 0){ pr_err("[%s] SBL Magic mismatch for avm_sbl_boot_string\n", __FUNCTION__); return 0; } pr_info("SBL Boot Info Version %d%s Boot TZ %d Boot Eva %d\n", sbl_status->sbl_version, (sbl_status->sbl_modified ? "M" : ""), sbl_status->tz_boot_index, sbl_status->eva_boot_index); if(sbl_status->tz_verified[0]){ pr_info("TZ0 Version %d%s ", sbl_status->tz_version[0], (sbl_status->tz_modified[0] ? "M" : "")); } else{ pr_info("TZ0 not verified\n"); } if(sbl_status->tz_verified[1]){ pr_info("TZ1 Version %d%s\n", sbl_status->tz_version[1], (sbl_status->tz_modified[1] ? "M" : "")); } else{ pr_info("TZ1 not verified\n"); } if(sbl_status->eva_verified[0]){ pr_info("EVA0 Version %d%s\n", sbl_status->eva_version[0], (sbl_status->eva_modified[0] ? "M" : "")); } else{ pr_info("EVA0 not verified\n"); } if(sbl_status->eva_verified[1]){ pr_info("EVA1 Version %d%s\n", sbl_status->eva_version[1], (sbl_status->eva_modified[1] ? "M" : "")); } else{ pr_info("EVA1 not verified\n"); } sblprocdir = proc_mkdir("avm/sbl_boot_info", NULL); if(sblprocdir == NULL) { return 0; } add_simple_proc_file( "avm/sbl_boot_info/tz_boot_index", NULL, proc_tz_boot_index, NULL); add_simple_proc_file( "avm/sbl_boot_info/eva_boot_index", NULL, proc_eva_boot_index, NULL); add_simple_proc_file( "avm/sbl_boot_info/eva_boot_ack", proc_write_eva_boot_ack, proc_eva_boot_ack, NULL); add_simple_proc_file( "avm/sbl_boot_info/tz_boot_ack", proc_write_tz_boot_ack, proc_tz_boot_ack, NULL); add_simple_proc_file( "avm/sbl_boot_info/eva0_verified", NULL, proc_eva0_verified, NULL); add_simple_proc_file( "avm/sbl_boot_info/eva1_verified", NULL, proc_eva1_verified, NULL); add_simple_proc_file( "avm/sbl_boot_info/eva0_version", NULL, proc_eva0_version, NULL); add_simple_proc_file( "avm/sbl_boot_info/eva1_version", NULL, proc_eva1_version, NULL); add_simple_proc_file( "avm/sbl_boot_info/tz0_verified", NULL, proc_tz0_verified, NULL); add_simple_proc_file( "avm/sbl_boot_info/tz1_verified", NULL, proc_tz1_verified, NULL); add_simple_proc_file( "avm/sbl_boot_info/tz0_version", NULL, proc_tz0_version, NULL); add_simple_proc_file( "avm/sbl_boot_info/tz1_version", NULL, proc_tz1_version, NULL); add_simple_proc_file( "avm/sbl_boot_info/sbl_version", NULL, proc_sbl_version, NULL); return 0; } late_initcall(proc_sbl_boot_status); #endif /* #if defined(CONFIG_PROC_FS) */