1 /* SPDX-License-Identifier: GPL-2.0-only */
4 #include <device/pci_ops.h>
5 #include <console/console.h>
7 #include <device/pci_def.h>
9 #include <southbridge/intel/common/me.h>
14 static const char *me_ack_values
[] = {
15 [ME_HFS_ACK_NO_DID
] = "No DID Ack received",
16 [ME_HFS_ACK_RESET
] = "Non-power cycle reset",
17 [ME_HFS_ACK_PWR_CYCLE
] = "Power cycle reset",
18 [ME_HFS_ACK_S3
] = "Go to S3",
19 [ME_HFS_ACK_S4
] = "Go to S4",
20 [ME_HFS_ACK_S5
] = "Go to S5",
21 [ME_HFS_ACK_GBL_RESET
] = "Global Reset",
22 [ME_HFS_ACK_CONTINUE
] = "Continue to boot"
25 void intel_early_me_status(void)
29 u32 id
= pci_read_config32(PCH_ME_DEV
, PCI_VENDOR_ID
);
31 if ((id
== 0xffffffff) || (id
== 0x00000000) ||
32 (id
== 0x0000ffff) || (id
== 0xffff0000)) {
33 printk(BIOS_DEBUG
, "Missing Intel ME PCI device.\n");
35 hfs
.raw
= pci_read_config32(PCH_ME_DEV
, PCI_ME_HFS
);
36 gmes
.raw
= pci_read_config32(PCH_ME_DEV
, PCI_ME_GMES
);
38 intel_me_status(&hfs
, &gmes
);
42 int intel_early_me_init(void)
48 printk(BIOS_INFO
, "Intel ME early init\n");
50 /* Wait for ME UMA SIZE VALID bit to be set */
51 for (count
= ME_RETRY
; count
> 0; --count
) {
52 uma
.raw
= pci_read_config32(PCH_ME_DEV
, PCI_ME_UMA
);
58 printk(BIOS_ERR
, "ME is not ready!\n");
62 /* Check for valid firmware */
63 hfs
.raw
= pci_read_config32(PCH_ME_DEV
, PCI_ME_HFS
);
65 printk(BIOS_WARNING
, "ME has bad firmware\n");
69 printk(BIOS_INFO
, "Intel ME firmware is ready\n");
73 int intel_early_me_uma_size(void)
77 uma
.raw
= pci_read_config32(PCH_ME_DEV
, PCI_ME_UMA
);
79 printk(BIOS_DEBUG
, "ME: Requested %uMB UMA\n", uma
.size
);
83 printk(BIOS_DEBUG
, "ME: Invalid UMA size\n");
87 int intel_early_me_init_done(u8 status
)
91 u32 mebase_l
, mebase_h
;
94 .init_done
= ME_INIT_DONE
,
98 /* MEBASE from MESEG_BASE[35:20] */
99 mebase_l
= pci_read_config32(PCI_CPU_DEVICE
, PCI_CPU_MEBASE_L
);
100 mebase_h
= pci_read_config32(PCI_CPU_DEVICE
, PCI_CPU_MEBASE_H
) & 0xf;
101 did
.uma_base
= (mebase_l
>> 20) | (mebase_h
<< 12);
103 /* Send message to ME */
104 printk(BIOS_DEBUG
, "ME: Sending Init Done with status: %d, "
105 "UMA base: 0x%04x\n", status
, did
.uma_base
);
107 pci_write_config32(PCH_ME_DEV
, PCI_ME_H_GS
, did
.raw
);
109 /* Must wait for ME acknowledgement */
110 for (count
= ME_RETRY
; count
> 0; --count
) {
111 hfs
.raw
= pci_read_config32(PCH_ME_DEV
, PCI_ME_HFS
);
112 if (hfs
.bios_msg_ack
)
117 printk(BIOS_ERR
, "ME failed to respond\n");
121 /* Return the requested BIOS action */
122 printk(BIOS_NOTICE
, "ME: Requested BIOS Action: %s\n",
123 me_ack_values
[hfs
.ack_data
]);
125 /* Check status after acknowledgement */
126 intel_early_me_status();
129 switch (hfs
.ack_data
) {
130 case ME_HFS_ACK_CONTINUE
:
131 /* Continue to boot */
133 case ME_HFS_ACK_RESET
:
134 /* Non-power cycle reset */
138 case ME_HFS_ACK_PWR_CYCLE
:
139 /* Power cycle reset */
143 case ME_HFS_ACK_GBL_RESET
:
154 /* Perform the requested reset */