| .. | .. |
|---|
| 16 | 16 | * respective wildcard entries. |
|---|
| 17 | 17 | * |
|---|
| 18 | 18 | * A typical table entry would be to match a specific CPU |
|---|
| 19 | | - * { X86_VENDOR_INTEL, 6, 0x12 } |
|---|
| 20 | | - * or to match a specific CPU feature |
|---|
| 21 | | - * { X86_FEATURE_MATCH(X86_FEATURE_FOOBAR) } |
|---|
| 19 | + * |
|---|
| 20 | + * X86_MATCH_VENDOR_FAM_MODEL_FEATURE(INTEL, 6, INTEL_FAM6_BROADWELL, |
|---|
| 21 | + * X86_FEATURE_ANY, NULL); |
|---|
| 22 | 22 | * |
|---|
| 23 | 23 | * Fields can be wildcarded with %X86_VENDOR_ANY, %X86_FAMILY_ANY, |
|---|
| 24 | | - * %X86_MODEL_ANY, %X86_FEATURE_ANY or 0 (except for vendor) |
|---|
| 24 | + * %X86_MODEL_ANY, %X86_FEATURE_ANY (except for vendor) |
|---|
| 25 | + * |
|---|
| 26 | + * asm/cpu_device_id.h contains a set of useful macros which are shortcuts |
|---|
| 27 | + * for various common selections. The above can be shortened to: |
|---|
| 28 | + * |
|---|
| 29 | + * X86_MATCH_INTEL_FAM6_MODEL(BROADWELL, NULL); |
|---|
| 25 | 30 | * |
|---|
| 26 | 31 | * Arrays used to match for this should also be declared using |
|---|
| 27 | 32 | * MODULE_DEVICE_TABLE(x86cpu, ...) |
|---|
| .. | .. |
|---|
| 53 | 58 | return NULL; |
|---|
| 54 | 59 | } |
|---|
| 55 | 60 | EXPORT_SYMBOL(x86_match_cpu); |
|---|
| 61 | + |
|---|
| 62 | +static const struct x86_cpu_desc * |
|---|
| 63 | +x86_match_cpu_with_stepping(const struct x86_cpu_desc *match) |
|---|
| 64 | +{ |
|---|
| 65 | + struct cpuinfo_x86 *c = &boot_cpu_data; |
|---|
| 66 | + const struct x86_cpu_desc *m; |
|---|
| 67 | + |
|---|
| 68 | + for (m = match; m->x86_family | m->x86_model; m++) { |
|---|
| 69 | + if (c->x86_vendor != m->x86_vendor) |
|---|
| 70 | + continue; |
|---|
| 71 | + if (c->x86 != m->x86_family) |
|---|
| 72 | + continue; |
|---|
| 73 | + if (c->x86_model != m->x86_model) |
|---|
| 74 | + continue; |
|---|
| 75 | + if (c->x86_stepping != m->x86_stepping) |
|---|
| 76 | + continue; |
|---|
| 77 | + return m; |
|---|
| 78 | + } |
|---|
| 79 | + return NULL; |
|---|
| 80 | +} |
|---|
| 81 | + |
|---|
| 82 | +bool x86_cpu_has_min_microcode_rev(const struct x86_cpu_desc *table) |
|---|
| 83 | +{ |
|---|
| 84 | + const struct x86_cpu_desc *res = x86_match_cpu_with_stepping(table); |
|---|
| 85 | + |
|---|
| 86 | + if (!res || res->x86_microcode_rev > boot_cpu_data.microcode) |
|---|
| 87 | + return false; |
|---|
| 88 | + |
|---|
| 89 | + return true; |
|---|
| 90 | +} |
|---|
| 91 | +EXPORT_SYMBOL_GPL(x86_cpu_has_min_microcode_rev); |
|---|