File: intel_microcode.h

package info (click to toggle)
iucode-tool 2.3.1-3
  • links: PTS, VCS
  • area: main
  • in suites: bookworm, forky, sid, trixie
  • size: 860 kB
  • sloc: sh: 4,178; ansic: 3,155; makefile: 23
file content (159 lines) | stat: -rw-r--r-- 5,574 bytes parent folder | download | duplicates (2)
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
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
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
/*
 *  Intel CPU Microcode data manipulation
 *
 *  Copyright (c) 2000-2006 Tigran Aivazian <tigran@aivazian.fsnet.co.uk>
 *                2006      Shaohua Li <shaohua.li@intel.com>
 *                2010-2018 Henrique de Moraes Holschuh <hmh@hmh.eng.br>
 *
 *  Based on Linux kernel Intel Microcode driver v2.6.36-rc3 (1.14)
 *  Based on Linux microcode.ctl version 1.17
 *
 *  Reference: Section 9.11 of Volume 3a, IA-32 Intel Architecture
 *  Software Developer's Manual
 *  Order Number 253668 or free download from:
 *  http://developer.intel.com/design/pentium4/manuals/253668.htm
 *
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation; either version 2 of the License, or
 *  (at your option) any later version.
 */

#ifndef INTEL_MICROCODE_H
#define INTEL_MICROCODE_H

#include "iucode_tool_config.h"

#include <stdint.h>
#include <sys/types.h>

/* Minimum object size that could have a valid production microcode */
#define INTEL_UC_MINSIZE 1024

typedef enum { /* status result codes */
	INTEL_UCODE_NOERROR = 0,
	INTEL_UCODE_BAD_PARAMETERS,
	INTEL_UCODE_INVALID_DATA,
	INTEL_UCODE_UNKNOWN_FORMAT,
	/* only returned by intel_ucode_check_microcode() */
	INTEL_UCODE_BAD_EXTENDED_TABLE,
	INTEL_UCODE_BAD_EXTENDED_TABLE_CHECKSUM,
	INTEL_UCODE_BAD_EXTENDED_SIG_CHECKSUM,
	INTEL_UCODE_BAD_CHECKSUM,
	/* only returned by the foreach functions */
	INTEL_UCODE_CALLBACK_ERROR,
	INTEL_UCODE_COUNTEROVERFLOW,
} intel_ucode_status_t;

struct intel_ucode_metadata {
	uint16_t	date_year;	/* 4-bit packed BCD format */
	uint8_t		date_day;	/* 4-bit packed BCD format */
	uint8_t		date_month;	/* 4-bit packed BCD format */
	int32_t		revision;
	uint32_t	size;
	uint32_t	extsig_count;
};

intel_ucode_status_t intel_ucode_getmetadata(const void * const uc,
				struct intel_ucode_metadata * const metadata);

uint32_t intel_ucode_getdate_bcd(const void * const uc);

/**
 * intel_ucode_sigmatch() - match signature against processor signature
 *
 * @s1:    CPUID 0x01, EAX
 * @s2:    microcode signature/extended signature "sig" field
 * @p1:    1 << (MSR IA32_PLATFORM_ID[52:50])
 * @p2:    microcode signature/extended signature "pf" mask
 *
 * Returns true if the microcode can be used in a given processor.
 *
 * The kernel driver exports through sysfs the processor flags already
 * in the format expected by this macro.
 */
#define intel_ucode_sigmatch(s1, s2, p1, p2) \
	(((s1) == (s2)) && (((p1) & (p2)) || (((p1) == 0) && ((p2) == 0))))

const char * intel_ucode_errstr(const intel_ucode_status_t status) __attribute__((const));

intel_ucode_status_t intel_ucode_check_microcode(const void * const uc,
						 const size_t maxlen,
						 const int strict);

int intel_ucode_compare(const void * const uc1, const void * const uc2);

int intel_ucode_scan_for_microcode(const void ** const bs,
				   const void ** const be,
				   size_t * const blen,
				   size_t * const alen);

/* Iterators */

/**
 * intel_ucode_sig_callback() - callback function for the
 *                             intel_ucode_foreach_microcode() function
 *
 * @userdata:    pointer as passed to intel_ucode_foreach_microcode()
 * @uc_count:    one-based counter of microcode entries
 * @uc:          pointer to start of microcode entry
 * @uc_max_size: maximum bound for microcode entry size
 *
 * @uc is a pointer to somewhere inside the original bundle passed to
 * intel_ucode_foreach_microcode(), where a microcode entry starts.
 * DO NOT MODIFY the memory area pointed by @uc.
 *
 * Note that it is very likely that the callback will HAVE to call
 * intel_ucode_check_microcode(uc) to check the microcode entry, and
 * return non-zero should it is faulty, otherwise nasty things can
 * happen.
 *
 * If the callback returns a non-zero value, the foreach operation
 * is aborted with a INTEL_UCODE_CALLBACK_ERROR error.
 */
typedef int (intel_ucode_uc_callback)(void * const userdata,
					const unsigned int uc_count,
					const void * const uc,
					const size_t uc_max_size);

intel_ucode_status_t intel_ucode_foreach_microcode(
			const void * const uc_bundle,
			const size_t uc_bundle_size,
			intel_ucode_uc_callback * const action,
			void * const userdata);

/**
 * intel_ucode_sig_callback() - callback function for the
 *                             intel_ucode_foreach_signature() function
 *
 * @userdata:		pointer as passed to intel_ucode_foreach_signature()
 * @sig_count:		zero-based counter of signatures on this microcode
 * @cpuid:		cpuid this microcode applies to
 * @pf_mask:		processor flags mask this microcode applies to
 * @uc_data:		microcode data
 * @uc_data_size:	microcode data size
 * @uc:			microcode entry (headers and data)
 * @uc_size:		microcode entry size
 *
 * DO NOT MODIFY THE MEMORY AREAS REFERENCED BY @uc_data and @uc.
 *
 * The callback can obtain data about the microcode through
 * a call to intel_ucode_getmetadata(uc, metadata).
 *
 * If the callback returns a non-zero value, the foreach operation
 * is aborted with a INTEL_UCODE_CALLBACK_ERROR error.
 */
typedef int (intel_ucode_sig_callback)(void * const userdata,
				const unsigned int sig_count,
				const uint32_t cpuid,
				const uint32_t pf_mask,
				const void * const uc_data,
				const unsigned int uc_data_size,
				const void * const uc,
				const unsigned int uc_size);

intel_ucode_status_t intel_ucode_foreach_signature(const void * const uc,
				intel_ucode_sig_callback * const action,
				void * const userdata);

#endif /* INTEL_MICROCODE_H */