Lines Matching +full:check +full:- +full:patch
1 // SPDX-License-Identifier: GPL-2.0-only
8 * Copyright (C) 2008-2011 Advanced Micro Devices Inc.
9 * 2013-2018 Borislav Petkov <[email protected]>
125 * microcode patch we found to match.
135 * Microcode patch container file is prepended to the initrd in cpio
146 * 2. To match which patches to load because the patch revision ID
166 if (patch_id == pd->patch_id) in cmp_id()
168 else if (patch_id < pd->patch_id) in cmp_id()
169 return -1; in cmp_id()
211 …pr_info("You should not be seeing this. Please send the following couple of lines to x86-<at>-kern… in need_sha_check()
234 pr_err("No sha256 digest for patch ID: 0x%x found\n", patch_id); in verify_sha256_digest()
242 if (memcmp(digest, pd->sha256, sizeof(digest))) { in verify_sha256_digest()
243 pr_err("Patch 0x%x SHA256 digest mismatch!\n", patch_id); in verify_sha256_digest()
289 if (!et || !et->num_entries) in find_equiv_id()
292 for (i = 0; i < et->num_entries; i++) { in find_equiv_id()
293 struct equiv_cpu_entry *e = &et->entry[i]; in find_equiv_id()
295 if (sig == e->installed_cpu) in find_equiv_id()
296 return e->equiv_cpu; in find_equiv_id()
302 * Check whether there is a valid microcode container file at the beginning
324 * Check whether there is a valid, non-truncated CPU equivalence table at the
346 buf_size -= CONTAINER_HDR_SZ; in verify_equivalence_table()
359 * Check whether there is a valid, non-truncated microcode patch section at the
362 * On success, @sh_psize returns the patch size according to the section header,
371 pr_debug("Truncated patch section.\n"); in __verify_patch_section()
386 pr_debug("Patch of size %u too short.\n", p_size); in __verify_patch_section()
396 * Check whether the passed remaining file @buf_size is large enough to contain
397 * a patch of the indicated @sh_psize (and also whether this size does not
398 * exceed the per-family maximum). @sh_psize is the size read from the section
433 * Verify the patch in @buf.
437 * positive: patch is not for this family, skip it
449 return -1; in verify_patch()
456 buf_size -= SECTION_HDR_SIZE; in verify_patch()
459 * Check if the remaining buffer is big enough to contain a patch of in verify_patch()
463 pr_debug("Patch of size %u truncated.\n", sh_psize); in verify_patch()
464 return -1; in verify_patch()
468 pr_debug("Per-family patch size mismatch.\n"); in verify_patch()
469 return -1; in verify_patch()
475 if (mc_hdr->nb_dev_id || mc_hdr->sb_dev_id) { in verify_patch()
476 pr_err("Patch-ID 0x%08x: chipset-specific code unsupported.\n", mc_hdr->patch_id); in verify_patch()
477 return -1; in verify_patch()
480 proc_id = mc_hdr->processor_rev_id; in verify_patch()
492 return ucode_rev_to_cpuid(mc->hdr.patch_id).full == bsp_cpuid_1_eax; in mc_patch_matches()
494 return eq_id == mc->hdr.processor_rev_id; in mc_patch_matches()
522 * doesn't contain a patch for the CPU, scan through the whole container in parse_container()
528 size -= hdr[2] + CONTAINER_HDR_SZ; in parse_container()
532 * some basic sanity-checking too. in parse_container()
542 * Patch verification failed, skip to the next container, if in parse_container()
543 * there is one. Before exit, check whether that container has in parse_container()
544 * found a patch already. If so, use it. in parse_container()
553 desc->psize = patch_size; in parse_container()
554 desc->mc = mc; in parse_container()
558 /* Skip patch section header too: */ in parse_container()
560 size -= patch_size + SECTION_HDR_SIZE; in parse_container()
565 * If we have found a patch (desc->mc), it means we're looking at the in parse_container()
566 * container which has a patch for this CPU so return 0 to mean, @ucode in parse_container()
571 if (desc->mc) { in parse_container()
572 desc->data = ucode; in parse_container()
573 desc->size = orig_size - size; in parse_container()
578 return orig_size - size; in parse_container()
595 size -= s; in scan_containers()
605 unsigned long p_addr = (unsigned long)&mc->hdr.data_code; in __apply_microcode_amd()
607 if (!verify_sha256_digest(mc->hdr.patch_id, *cur_rev, (const u8 *)p_addr, psize)) in __apply_microcode_amd()
613 unsigned long p_addr_end = p_addr + psize - 1; in __apply_microcode_amd()
618 * Flush next page too if patch image is crossing a page in __apply_microcode_amd()
625 /* verify patch application was successful */ in __apply_microcode_amd()
627 if (*cur_rev != mc->hdr.patch_id) in __apply_microcode_amd()
635 char fw_name[36] = "amd-ucode/microcode_amd.bin"; in get_builtin_microcode()
644 "amd-ucode/microcode_amd_fam%02hhxh.bin", family); in get_builtin_microcode()
647 cp->size = fw.size; in get_builtin_microcode()
648 cp->data = (void *)fw.data; in get_builtin_microcode()
672 * patch container file in initrd, traverse equivalent cpu table, look for a
673 * matching microcode patch, and update, all in initrd memory in place.
674 * When vmalloc() is available for use later -- on 64-bit during first AP load,
675 * and on 32-bit during save_microcode_in_initrd() -- we can call
690 pr_warn_once("It is a very very bad idea to disable the blobs SHA check!\n"); in load_ucode_amd_bsp()
698 ed->old_rev = rev; in load_ucode_amd_bsp()
713 * Allow application of the same revision to pick up SMT-specific in load_ucode_amd_bsp()
715 * up-to-date. in load_ucode_amd_bsp()
717 if (ed->old_rev > mc->hdr.patch_id) in load_ucode_amd_bsp()
721 ed->new_rev = rev; in load_ucode_amd_bsp()
728 /* Zen and newer hardcode the f/m/s in the patch ID */ in patch_cpus_equivalent()
730 union cpuid_1_eax p_cid = ucode_rev_to_cpuid(p->patch_id); in patch_cpus_equivalent()
731 union cpuid_1_eax n_cid = ucode_rev_to_cpuid(n->patch_id); in patch_cpus_equivalent()
740 return p->equiv_cpu == n->equiv_cpu; in patch_cpus_equivalent()
745 * a small, trivial cache of per-family ucode patches
753 n.patch_id = uci->cpu_sig.rev; in cache_find_patch()
766 /* Zen and newer hardcode the f/m/s in the patch ID */ in patch_newer()
770 zp.ucode_rev = p->patch_id; in patch_newer()
771 zn.ucode_rev = n->patch_id; in patch_newer()
774 return -1; in patch_newer()
778 return n->patch_id > p->patch_id; in patch_newer()
793 /* we already have the latest patch */ in update_cache()
794 kfree(new_patch->data); in update_cache()
799 list_replace(&p->plist, &new_patch->plist); in update_cache()
800 kfree(p->data); in update_cache()
805 /* no patch found, add it */ in update_cache()
806 list_add_tail(&new_patch->plist, µcode_cache); in update_cache()
814 __list_del(p->plist.prev, p->plist.next); in free_cache()
815 kfree(p->data); in free_cache()
825 uci->cpu_sig.rev = get_patch_level(); in find_patch()
828 equiv_id = find_equiv_id(&equiv_table, uci->cpu_sig.sig); in find_patch()
846 mc = p->data; in reload_ucode_amd()
849 if (rev < mc->hdr.patch_id) { in reload_ucode_amd()
850 if (__apply_microcode_amd(mc, &rev, p->size)) in reload_ucode_amd()
860 csig->sig = cpuid_eax(0x00000001); in collect_cpu_info_amd()
861 csig->rev = get_patch_level(); in collect_cpu_info_amd()
864 * a patch could have been loaded early, set uci->mc so that in collect_cpu_info_amd()
868 if (p && (p->patch_id == csig->rev)) in collect_cpu_info_amd()
869 uci->mc = p->data; in collect_cpu_info_amd()
891 rev = uci->cpu_sig.rev; in apply_microcode_amd()
893 mc_amd = p->data; in apply_microcode_amd()
894 uci->mc = p->data; in apply_microcode_amd()
896 /* need to apply patch? */ in apply_microcode_amd()
897 if (rev > mc_amd->hdr.patch_id) { in apply_microcode_amd()
902 if (!__apply_microcode_amd(mc_amd, &rev, p->size)) { in apply_microcode_amd()
904 cpu, mc_amd->hdr.patch_id); in apply_microcode_amd()
908 rev = mc_amd->hdr.patch_id; in apply_microcode_amd()
912 uci->cpu_sig.rev = rev; in apply_microcode_amd()
913 c->microcode = rev; in apply_microcode_amd()
916 if (c->cpu_index == boot_cpu_data.cpu_index) in apply_microcode_amd()
975 * Return a non-negative value even if some of the checks failed so that
976 * we can skip over the next patch. If we return a negative value, we
985 struct ucode_patch *patch; in verify_and_add_patch() local
993 patch = kzalloc(sizeof(*patch), GFP_KERNEL); in verify_and_add_patch()
994 if (!patch) { in verify_and_add_patch()
995 pr_err("Patch allocation failure.\n"); in verify_and_add_patch()
996 return -EINVAL; in verify_and_add_patch()
999 patch->data = kmemdup(fw + SECTION_HDR_SIZE, *patch_size, GFP_KERNEL); in verify_and_add_patch()
1000 if (!patch->data) { in verify_and_add_patch()
1001 pr_err("Patch data allocation failure.\n"); in verify_and_add_patch()
1002 kfree(patch); in verify_and_add_patch()
1003 return -EINVAL; in verify_and_add_patch()
1005 patch->size = *patch_size; in verify_and_add_patch()
1008 proc_id = mc_hdr->processor_rev_id; in verify_and_add_patch()
1010 INIT_LIST_HEAD(&patch->plist); in verify_and_add_patch()
1011 patch->patch_id = mc_hdr->patch_id; in verify_and_add_patch()
1012 patch->equiv_cpu = proc_id; in verify_and_add_patch()
1015 __func__, patch->patch_id, proc_id); in verify_and_add_patch()
1018 update_cache(patch); in verify_and_add_patch()
1034 size -= offset; in __load_microcode_amd()
1051 size -= (crnt_size + SECTION_HDR_SIZE); in __load_microcode_amd()
1090 if (c->microcode >= p->patch_id) in load_microcode_amd()
1107 if (dis_ucode_ldr || c->x86_vendor != X86_VENDOR_AMD || c->x86 < 0x10) in save_microcode_in_initrd()
1111 return -EINVAL; in save_microcode_in_initrd()
1115 return -EINVAL; in save_microcode_in_initrd()
1119 return -EINVAL; in save_microcode_in_initrd()
1129 * amd-ucode/microcode_amd.bin
1133 * Beginning with family 15h, they are in family-specific firmware files:
1135 * amd-ucode/microcode_amd_fam15h.bin
1136 * amd-ucode/microcode_amd_fam16h.bin
1143 char fw_name[36] = "amd-ucode/microcode_amd.bin"; in request_microcode_amd()
1151 if (c->x86 >= 0x15) in request_microcode_amd()
1152 snprintf(fw_name, sizeof(fw_name), "amd-ucode/microcode_amd_fam%.2xh.bin", c->x86); in request_microcode_amd()
1160 if (!verify_container(fw->data, fw->size)) in request_microcode_amd()
1163 ret = load_microcode_amd(c->x86, fw->data, fw->size); in request_microcode_amd()
1176 uci->mc = NULL; in microcode_fini_cpu_amd()
1191 if (c->x86_vendor != X86_VENDOR_AMD || c->x86 < 0x10) { in init_amd_microcode()
1192 pr_warn("AMD CPU family 0x%x not supported\n", c->x86); in init_amd_microcode()