Blame view
common/image-android-dt.c
4.29 KB
c04473345 common: Add suppo... |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 |
// SPDX-License-Identifier: GPL-2.0+ /* * (C) Copyright 2018 Linaro Ltd. * Sam Protsenko <semen.protsenko@linaro.org> */ #include <image-android-dt.h> #include <dt_table.h> #include <common.h> #include <linux/libfdt.h> #include <mapmem.h> /** * Check if image header is correct. * * @param hdr_addr Start address of DT image * @return true if header is correct or false if header is incorrect */ bool android_dt_check_header(ulong hdr_addr) { const struct dt_table_header *hdr; u32 magic; hdr = map_sysmem(hdr_addr, sizeof(*hdr)); magic = fdt32_to_cpu(hdr->magic); unmap_sysmem(hdr); return magic == DT_TABLE_MAGIC; } /** * Get the address of FDT (dtb or dtbo) in memory by its index in image. * * @param hdr_addr Start address of DT image * @param index Index of desired FDT in image (starting from 0) * @param[out] addr If not NULL, will contain address to specified FDT * @param[out] size If not NULL, will contain size of specified FDT * * @return true on success or false on error */ bool android_dt_get_fdt_by_index(ulong hdr_addr, u32 index, ulong *addr, u32 *size) { const struct dt_table_header *hdr; const struct dt_table_entry *e; u32 entry_count, entries_offset, entry_size; ulong e_addr; u32 dt_offset, dt_size; hdr = map_sysmem(hdr_addr, sizeof(*hdr)); entry_count = fdt32_to_cpu(hdr->dt_entry_count); entries_offset = fdt32_to_cpu(hdr->dt_entries_offset); entry_size = fdt32_to_cpu(hdr->dt_entry_size); unmap_sysmem(hdr); |
e63bf1b13 common: image-and... |
55 56 57 |
if (index >= entry_count) { printf("Error: index >= dt_entry_count (%u >= %u) ", index, |
c04473345 common: Add suppo... |
58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 |
entry_count); return false; } e_addr = hdr_addr + entries_offset + index * entry_size; e = map_sysmem(e_addr, sizeof(*e)); dt_offset = fdt32_to_cpu(e->dt_offset); dt_size = fdt32_to_cpu(e->dt_size); unmap_sysmem(e); if (addr) *addr = hdr_addr + dt_offset; if (size) *size = dt_size; return true; } #if !defined(CONFIG_SPL_BUILD) static void android_dt_print_fdt_info(const struct fdt_header *fdt) { u32 fdt_size; int root_node_off; |
24434adbd common: image-and... |
81 |
const char *compatible; |
c04473345 common: Add suppo... |
82 |
|
c04473345 common: Add suppo... |
83 84 85 86 |
root_node_off = fdt_path_offset(fdt, "/"); if (root_node_off < 0) { printf("Error: Root node not found "); |
24434adbd common: image-and... |
87 |
return; |
c04473345 common: Add suppo... |
88 |
} |
24434adbd common: image-and... |
89 90 91 |
fdt_size = fdt_totalsize(fdt); compatible = fdt_getprop(fdt, root_node_off, "compatible", NULL); |
c04473345 common: Add suppo... |
92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 |
printf(" (FDT)size = %d ", fdt_size); printf(" (FDT)compatible = %s ", compatible ? compatible : "(unknown)"); } /** * Print information about DT image structure. * * @param hdr_addr Start address of DT image */ void android_dt_print_contents(ulong hdr_addr) { const struct dt_table_header *hdr; u32 entry_count, entries_offset, entry_size; u32 i; hdr = map_sysmem(hdr_addr, sizeof(*hdr)); entry_count = fdt32_to_cpu(hdr->dt_entry_count); entries_offset = fdt32_to_cpu(hdr->dt_entries_offset); entry_size = fdt32_to_cpu(hdr->dt_entry_size); /* Print image header info */ printf("dt_table_header: "); printf(" magic = %08x ", fdt32_to_cpu(hdr->magic)); printf(" total_size = %d ", fdt32_to_cpu(hdr->total_size)); printf(" header_size = %d ", fdt32_to_cpu(hdr->header_size)); printf(" dt_entry_size = %d ", entry_size); printf(" dt_entry_count = %d ", entry_count); printf(" dt_entries_offset = %d ", entries_offset); printf(" page_size = %d ", fdt32_to_cpu(hdr->page_size)); printf(" version = %d ", fdt32_to_cpu(hdr->version)); unmap_sysmem(hdr); /* Print image entries info */ for (i = 0; i < entry_count; ++i) { const ulong e_addr = hdr_addr + entries_offset + i * entry_size; const struct dt_table_entry *e; const struct fdt_header *fdt; u32 dt_offset, dt_size; u32 j; e = map_sysmem(e_addr, sizeof(*e)); dt_offset = fdt32_to_cpu(e->dt_offset); dt_size = fdt32_to_cpu(e->dt_size); printf("dt_table_entry[%d]: ", i); printf(" dt_size = %d ", dt_size); printf(" dt_offset = %d ", dt_offset); printf(" id = %08x ", fdt32_to_cpu(e->id)); printf(" rev = %08x ", fdt32_to_cpu(e->rev)); for (j = 0; j < 4; ++j) { printf(" custom[%d] = %08x ", j, fdt32_to_cpu(e->custom[j])); } unmap_sysmem(e); /* Print FDT info for this entry */ fdt = map_sysmem(hdr_addr + dt_offset, sizeof(*fdt)); android_dt_print_fdt_info(fdt); unmap_sysmem(fdt); } } #endif |