From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from aserp2120.oracle.com (aserp2120.oracle.com [141.146.126.78]) by mx.groups.io with SMTP id smtpd.web08.32137.1613978387296919807 for ; Sun, 21 Feb 2021 23:19:47 -0800 Authentication-Results: mx.groups.io; dkim=pass header.i=@oracle.com header.s=corp-2020-01-29 header.b=UpfzfXdw; spf=pass (domain: oracle.com, ip: 141.146.126.78, mailfrom: ankur.a.arora@oracle.com) Received: from pps.filterd (aserp2120.oracle.com [127.0.0.1]) by aserp2120.oracle.com (8.16.0.42/8.16.0.42) with SMTP id 11M7Dv4e131242; Mon, 22 Feb 2021 07:19:43 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=oracle.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : content-transfer-encoding : content-type : mime-version; s=corp-2020-01-29; bh=LRmSgHeU2Z8fSi2Ls38i75CZGzgGp6EbcgbHjRODjIU=; b=UpfzfXdwn0sIvU6JkUG/M8b6ovlzPnYHgSQLkEnYeArNaEY2NSBsQBGmILgrBPYnCfXn 1+EDQLoeyX7KixBNw30NdMWIF872Hw6Vcv6LaDOZMPvyGz8JxwOtrYTm+SXDqNKKiX+r y7YoSSSBWHJIT2UMJHIoHYw7Cm31UIJ3GHYxuN9v5lja475dNrRjRm/Q6J2ORlXmBOoQ xJ1JDtilOxLsKAhe88rdT8dD9U6DO8eDawEPt1jOUa34wmU50iwlkOqyM+H1vojIt5l0 XEwkRCbbLvua1fuYG5yVbR3PfKBTwzTTLX95fqu+SuONxU4Rgo5BhmS0Q4S282yjACf2 LQ== Received: from userp3020.oracle.com (userp3020.oracle.com [156.151.31.79]) by aserp2120.oracle.com with ESMTP id 36ttcm2ke6-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK); Mon, 22 Feb 2021 07:19:43 +0000 Received: from pps.filterd (userp3020.oracle.com [127.0.0.1]) by userp3020.oracle.com (8.16.0.42/8.16.0.42) with SMTP id 11M7GCDt126471; Mon, 22 Feb 2021 07:19:42 GMT Received: from nam12-dm6-obe.outbound.protection.outlook.com (mail-dm6nam12lp2175.outbound.protection.outlook.com [104.47.59.175]) by userp3020.oracle.com with ESMTP id 36uc6pynae-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK); Mon, 22 Feb 2021 07:19:42 +0000 ARC-Seal: i=1; a=rsa-sha256; s=arcselector9901; d=microsoft.com; cv=none; b=flr4z6yQlAxFaUCZ9MvKDtoNuUQZ+XW0SFRSSYA2HNlXknK+DbI4shM2+wD9X9C5PSJXQKkNRuWVl36I8kHRDIxf3u0f9Kj+Sv5zP+IFz7KK9oPyUW5Y2HRgkoxqAvVzmxQ01u4jJ0aOIS2opgBn3Ik6qwC/kBeU1QkZ6RbEq0qfAcMQ+hJf1nfXEg6QlV8SwaqJYpAhkVjv9jSCXu8nZ/8I2Z0fSNN1/ZItMBV8OouWgt8wd73+o2lHa7mt2SXnIY6/PUMU0zrD4YFkvTMvZ8raz8wIUK6kaujbA3GzQA1+nzDi6UmVR2m7HdLSGO1b0vpzOZ4VlZ9nyN+c5X6c4g== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector9901; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=LRmSgHeU2Z8fSi2Ls38i75CZGzgGp6EbcgbHjRODjIU=; b=FSRPC4FVq9x+56VbzB+G4l2Au80TDTZGRZ7817+Yuaaa3vEuyhJLJX+WDAV16PZKIB6ad1nlfUio5XHIvWVkfGjZ3RiXeE0WMpm1vKzkEPeZyH961wI5fk4kk36rg2Q0eu/qKDmRWM+doMcJ+vrBFGtbEoIgjs//i32/8dpmCPpjNQQAcyqqQyQdFxABydCYfo+aTCFQBtCKaNr+/Mj6BdOsIudzD9aZpYicydRdYOWX24eoSm4Qa9womfhos4r4OzoLYhilk8p6sjdp4eMwi7QJD8C1gFxqqo2xBhbQPg4N0XFjrN1fb14AkP3lczLQW5sxa2ZeExSszlSLWXePaQ== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass smtp.mailfrom=oracle.com; dmarc=pass action=none header.from=oracle.com; dkim=pass header.d=oracle.com; arc=none DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=oracle.onmicrosoft.com; s=selector2-oracle-onmicrosoft-com; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=LRmSgHeU2Z8fSi2Ls38i75CZGzgGp6EbcgbHjRODjIU=; b=sJNU6xn4K2LSo4P67PzsOwu/06Pod+nI7jg7u03T2zYvV9Y1yGVVMVS6MirzShOyYHKOlH8KPRwJ6BAU1GDeBHEIj7CYVWzvuD3V190KY/wZapG9/HTW5IWLTcyx+InN0HM0cQLs2p/R5blmmHiSQ1cURlLBQtxdGrMP2NZv46w= Authentication-Results: edk2.groups.io; dkim=none (message not signed) header.d=none;edk2.groups.io; dmarc=none action=none header.from=oracle.com; Received: from SJ0PR10MB4605.namprd10.prod.outlook.com (2603:10b6:a03:2d9::24) by BYAPR10MB3191.namprd10.prod.outlook.com (2603:10b6:a03:14f::29) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.3868.29; Mon, 22 Feb 2021 07:19:40 +0000 Received: from SJ0PR10MB4605.namprd10.prod.outlook.com ([fe80::a021:790:7ce6:6f16]) by SJ0PR10MB4605.namprd10.prod.outlook.com ([fe80::a021:790:7ce6:6f16%6]) with mapi id 15.20.3868.033; Mon, 22 Feb 2021 07:19:40 +0000 From: "Ankur Arora" To: devel@edk2.groups.io Cc: lersek@redhat.com, imammedo@redhat.com, boris.ostrovsky@oracle.com, Ankur Arora , Jordan Justen , Ard Biesheuvel , Aaron Young Subject: [PATCH v8 02/10] OvmfPkg/CpuHotplugSmm: collect hot-unplug events Date: Sun, 21 Feb 2021 23:19:20 -0800 Message-Id: <20210222071928.1401820-3-ankur.a.arora@oracle.com> X-Mailer: git-send-email 2.29.2 In-Reply-To: <20210222071928.1401820-1-ankur.a.arora@oracle.com> References: <20210222071928.1401820-1-ankur.a.arora@oracle.com> X-Originating-IP: [148.87.23.11] X-ClientProxiedBy: MWHPR17CA0065.namprd17.prod.outlook.com (2603:10b6:300:93::27) To SJ0PR10MB4605.namprd10.prod.outlook.com (2603:10b6:a03:2d9::24) MIME-Version: 1.0 X-MS-Exchange-MessageSentRepresentingType: 1 Received: from prion.us.oracle.com (148.87.23.11) by MWHPR17CA0065.namprd17.prod.outlook.com (2603:10b6:300:93::27) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.3868.27 via Frontend Transport; Mon, 22 Feb 2021 07:19:39 +0000 X-MS-PublicTrafficType: Email X-MS-Office365-Filtering-Correlation-Id: 28450373-8cec-48dc-8cdb-08d8d70237d2 X-MS-TrafficTypeDiagnostic: BYAPR10MB3191: X-MS-Exchange-Transport-Forked: True X-Microsoft-Antispam-PRVS: X-MS-Oob-TLC-OOBClassifiers: OLM:9508; X-MS-Exchange-SenderADCheck: 1 X-Microsoft-Antispam: BCL:0; X-Microsoft-Antispam-Message-Info: jIy8nUp7CD4yHpSSs07qaz6VCjPf675lCsXuStNWEy9jR1ja8DdAE3jo2QVeRi3k+2TYQCn33zptV1O7BRqImmwrU50zYl+pTGAHo/EsM/6MXfyyePRPFTWtrMiMDO3QObazYcauWmj5NhsBM6qEEtBiYneBzbWlJ9qAbDFhbhDClEcTDewtBVat+b4rJSv9Ih9j+5WUkCWr+U/t66UhFdnQlRWZ7QjwoHdJRnsX2XZhH2XGPwU6DQfyZBz5uC4EtV6WQis7zFqi3cSnzXsqTtTVog2AAB5xEGbsBxc/vHor48l8HtbmaT3Mrv+OZPbeMDL5aDo6NkJ+Zr/kANaa4LagYXcRb1KfiqNJm6NT6a9Q8fNs76is2FdvCD3S6KAF832SupVpC2D7otmFO+ZeL6h30aTgUJ7gtHyi5HBT8Ta1ZqEhK5hjFG7mAEhyUMtY4Y5IS5DFI6vzUwjmJ0RCU8U0AZuzPNSewTyr4WA5NS7ZITgHhgDjeC6IT1wM00EW8Bra/hlxj3Z7AioCLYkKtDBHnGadSjJLiTpn38wwuwZ/JHe6wJJdSvPUdD5ltVLS8qHC57eFeKYJDcXVOQS71DV7Cy++dUvwLvJb0X5cIcw= X-Forefront-Antispam-Report: CIP:255.255.255.255;CTRY:;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:SJ0PR10MB4605.namprd10.prod.outlook.com;PTR:;CAT:NONE;SFS:(39860400002)(136003)(346002)(376002)(396003)(366004)(2906002)(8936002)(54906003)(316002)(83380400001)(478600001)(86362001)(8676002)(6916009)(6486002)(2616005)(186003)(16526019)(956004)(26005)(107886003)(5660300002)(7696005)(52116002)(66946007)(6666004)(66476007)(66556008)(36756003)(1076003)(4326008)(966005)(103116003);DIR:OUT;SFP:1101; X-MS-Exchange-AntiSpam-MessageData: =?us-ascii?Q?ZhnGId06Wn2ooV9oTeUAA+SvF56tYUHU6i+NsGRQExWkl6nutGwN3w7Y6qX+?= =?us-ascii?Q?t1dlWiacBQzqrpJx0LBT5EPzNo5W6VUWb891UAKMn0zxWyYLBljzk0CktjEE?= =?us-ascii?Q?/2KAXL7BGjwcki9fpb6kFYJHHg4eu9TSHJglPUBqRFnaxwKQ89svnaRZ9Dm6?= =?us-ascii?Q?ae5gfXBgClFVXPdfOJkfTeEgNQXX5mvbVmGeychiMPIFbIbAqtLGROxlFICZ?= =?us-ascii?Q?OZWCkF+aRniJIkhy5lsJVKzuqjduaDy8Vwd3x8mRDwRjEhYLIvAP3Bu+Kf3C?= =?us-ascii?Q?ipiOGAe7X6B50bWEUYp08HWKLjqymiR9tjMLI7enJJIr0GNiDPDJzAy35MMa?= =?us-ascii?Q?zHCMfVf2XOG8yJz0h6ktpYLEBiKC4mgDUjCncc56se6Gn8SpaAEh5V/pFXvf?= =?us-ascii?Q?32W96MU9yAlbZlD32BsY3UcqZ7RsIqZBoQ9tn1Uuxc0DtLuhhVwgo26UIM53?= =?us-ascii?Q?piNbc7m6lDzeCODSJUYfGxIxDSRIdxwXaHMdgJNkwUoKxnnFWWU4uPj9XxTQ?= =?us-ascii?Q?KVUarKAUBAYezRjPDn/vkqQaKnCWzE9d4Y+CAwFMNPAgiPsRINup0NgOLT/q?= =?us-ascii?Q?4I8CzLGylXaJGdFLyVe4RRg5Dxs0gXLn0d3K50JL7Mdc+rs3oZ+CLAuIVJqk?= =?us-ascii?Q?kBqox4eAWFIt2wD91Vxn3UugAvfD4ZU+DnbnVIGgwB0dp4+b3I4VTEAfeug1?= =?us-ascii?Q?s2nqdZ3/ygMneefM2xFBix9To+P2QBJdGGsH4BjRQHLFbmW/Q+wZXQRU+IuD?= =?us-ascii?Q?5eNJyEwkbvwvJrabgi3DapoLd4tlV+oqokpr2mhrXkYVjJiGkvCyh09f74mf?= =?us-ascii?Q?aOsMQNAHznoJHYCL4VvUizIK+OHluKJfH/LeByxUBXNZ34FUJTh3ypOth8u2?= =?us-ascii?Q?i9AIVhGYe4ahJ1NDdkUoWs9tP/HxNZS0u2RvvaWMBPRYvZzVWEstrVyQn3wt?= =?us-ascii?Q?2a0FkbJVh4uMMio28rhDXgSAnkwI6k6PLout7yUw/mUH2PvtJVyD9UUp/jVT?= =?us-ascii?Q?HZQLj9oV2pwFhVgluxJQfjlx3aYtCf89ZK9Sk/I6xCrt5hjRO8wLL4ef1sN3?= =?us-ascii?Q?4ZZDHw7QwalbIIol1wFWoVaO3psMJFxv3QTMH1hyIsYuLLsDe90MEUlfr/9e?= =?us-ascii?Q?HHDYI0avR3jj26/8gGohiARYmWYWQK0ljYQM2H8gCGT2coamrtdwMrtJVPf1?= =?us-ascii?Q?q87EQdWLQkRx+1QYafvz5beZ9WrR+Jm2nVDNRgyLoH/msuPNrUmnA1GztzED?= =?us-ascii?Q?u/P1+xasovQm4193R23mvA6W8AqHdt+dalRdw5ydObfcF40bHcM56/GwT3Zb?= =?us-ascii?Q?md7yS1KUOCc1mn639d5p9yjU?= X-OriginatorOrg: oracle.com X-MS-Exchange-CrossTenant-Network-Message-Id: 28450373-8cec-48dc-8cdb-08d8d70237d2 X-MS-Exchange-CrossTenant-AuthSource: SJ0PR10MB4605.namprd10.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Internal X-MS-Exchange-CrossTenant-OriginalArrivalTime: 22 Feb 2021 07:19:40.0790 (UTC) X-MS-Exchange-CrossTenant-FromEntityHeader: Hosted X-MS-Exchange-CrossTenant-Id: 4e2c6054-71cb-48f1-bd6c-3a9705aca71b X-MS-Exchange-CrossTenant-MailboxType: HOSTED X-MS-Exchange-CrossTenant-UserPrincipalName: EjlBEqMLSBUtlfwWuWxY8sbIXFTJauL6oiwqLa/fucPZANn7t8fd4HHruIDSAyDeUwm6lOrdn+f4fiopzwavxm+nDEF0DfXf5BxBgZQPM/U= X-MS-Exchange-Transport-CrossTenantHeadersStamped: BYAPR10MB3191 X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=9902 signatures=668683 X-Proofpoint-Spam-Details: rule=notspam policy=default score=0 suspectscore=0 mlxscore=0 spamscore=0 mlxlogscore=999 adultscore=0 bulkscore=0 malwarescore=0 phishscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2009150000 definitions=main-2102220064 X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=9902 signatures=668683 X-Proofpoint-Spam-Details: rule=notspam policy=default score=0 mlxlogscore=999 adultscore=0 lowpriorityscore=0 spamscore=0 mlxscore=0 bulkscore=0 clxscore=1015 priorityscore=1501 malwarescore=0 impostorscore=0 suspectscore=0 phishscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2009150000 definitions=main-2102220064 Content-Transfer-Encoding: 8bit Content-Type: text/plain Process fw_remove events in QemuCpuhpCollectApicIds() and collect corresponding APIC IDs for CPUs that are being hot-unplugged. In addition, we now ignore CPUs which only have remove set. These CPUs haven't been processed by OSPM yet. This is based on the QEMU hot-unplug protocol documented here: https://lore.kernel.org/qemu-devel/20201204170939.1815522-3-imammedo@redhat.com/ Cc: Laszlo Ersek Cc: Jordan Justen Cc: Ard Biesheuvel Cc: Igor Mammedov Cc: Boris Ostrovsky Cc: Aaron Young Ref: https://bugzilla.tianocore.org/show_bug.cgi?id=3132 Signed-off-by: Ankur Arora --- Notes: Addresses the following review comments from v6: (1,4) Move (and also rename) QEMU_CPUHP_STAT_EJECTED to patch 8, where we actually use it. (2) Downgrade debug mask from DEBUG_INFO to DEBUG_VERBOSE. (3a,3b,3c) Keep the CurrentSelector increment operation at the tail of the loop. () As discussed elsewhere we also need to get the CpuSelector while collecting ApicIds in QemuCpuhpCollectApicIds(). This patch adds a separate parameter for the CpuSelector values, because that works better alongside the hotplug ExtendIds logic. OvmfPkg/CpuHotplugSmm/QemuCpuhp.h | 1 + OvmfPkg/Include/IndustryStandard/QemuCpuHotplug.h | 1 + OvmfPkg/CpuHotplugSmm/CpuHotplug.c | 21 +++++- OvmfPkg/CpuHotplugSmm/QemuCpuhp.c | 84 ++++++++++++++++------- 4 files changed, 79 insertions(+), 28 deletions(-) diff --git a/OvmfPkg/CpuHotplugSmm/QemuCpuhp.h b/OvmfPkg/CpuHotplugSmm/QemuCpuhp.h index 8adaa0ad91f0..1e23b150910e 100644 --- a/OvmfPkg/CpuHotplugSmm/QemuCpuhp.h +++ b/OvmfPkg/CpuHotplugSmm/QemuCpuhp.h @@ -55,6 +55,7 @@ QemuCpuhpCollectApicIds ( OUT APIC_ID *PluggedApicIds, OUT UINT32 *PluggedCount, OUT APIC_ID *ToUnplugApicIds, + OUT UINT32 *ToUnplugSelector, OUT UINT32 *ToUnplugCount ); diff --git a/OvmfPkg/Include/IndustryStandard/QemuCpuHotplug.h b/OvmfPkg/Include/IndustryStandard/QemuCpuHotplug.h index a34a6d3fae61..2ec7a107a64d 100644 --- a/OvmfPkg/Include/IndustryStandard/QemuCpuHotplug.h +++ b/OvmfPkg/Include/IndustryStandard/QemuCpuHotplug.h @@ -34,6 +34,7 @@ #define QEMU_CPUHP_STAT_ENABLED BIT0 #define QEMU_CPUHP_STAT_INSERT BIT1 #define QEMU_CPUHP_STAT_REMOVE BIT2 +#define QEMU_CPUHP_STAT_FW_REMOVE BIT4 #define QEMU_CPUHP_RW_CMD_DATA 0x8 diff --git a/OvmfPkg/CpuHotplugSmm/CpuHotplug.c b/OvmfPkg/CpuHotplugSmm/CpuHotplug.c index bf68fcd42914..3192bfea1f15 100644 --- a/OvmfPkg/CpuHotplugSmm/CpuHotplug.c +++ b/OvmfPkg/CpuHotplugSmm/CpuHotplug.c @@ -52,6 +52,7 @@ STATIC CPU_HOT_PLUG_DATA *mCpuHotPlugData; // STATIC APIC_ID *mPluggedApicIds; STATIC APIC_ID *mToUnplugApicIds; +STATIC UINT32 *mToUnplugSelector; // // Address of the non-SMRAM reserved memory page that contains the Post-SMM Pen // for hot-added CPUs. @@ -289,6 +290,7 @@ CpuHotplugMmi ( mPluggedApicIds, &PluggedCount, mToUnplugApicIds, + mToUnplugSelector, &ToUnplugCount ); if (EFI_ERROR (Status)) { @@ -333,7 +335,9 @@ CpuHotplugEntry ( ) { EFI_STATUS Status; + UINTN Len; UINTN Size; + UINTN SizeSel; // // This module should only be included when SMM support is required. @@ -387,8 +391,9 @@ CpuHotplugEntry ( // // Allocate the data structures that depend on the possible CPU count. // - if (RETURN_ERROR (SafeUintnSub (mCpuHotPlugData->ArrayLength, 1, &Size)) || - RETURN_ERROR (SafeUintnMult (sizeof (APIC_ID), Size, &Size))) { + if (RETURN_ERROR (SafeUintnSub (mCpuHotPlugData->ArrayLength, 1, &Len)) || + RETURN_ERROR (SafeUintnMult (sizeof (APIC_ID), Len, &Size))|| + RETURN_ERROR (SafeUintnMult (sizeof (UINT32), Len, &SizeSel))) { Status = EFI_ABORTED; DEBUG ((DEBUG_ERROR, "%a: invalid CPU_HOT_PLUG_DATA\n", __FUNCTION__)); goto Fatal; @@ -405,6 +410,12 @@ CpuHotplugEntry ( DEBUG ((DEBUG_ERROR, "%a: MmAllocatePool(): %r\n", __FUNCTION__, Status)); goto ReleasePluggedApicIds; } + Status = gMmst->MmAllocatePool (EfiRuntimeServicesData, SizeSel, + (VOID **)&mToUnplugSelector); + if (EFI_ERROR (Status)) { + DEBUG ((DEBUG_ERROR, "%a: MmAllocatePool(): %r\n", __FUNCTION__, Status)); + goto ReleaseToUnplugApicIds; + } // // Allocate the Post-SMM Pen for hot-added CPUs. @@ -412,7 +423,7 @@ CpuHotplugEntry ( Status = SmbaseAllocatePostSmmPen (&mPostSmmPenAddress, SystemTable->BootServices); if (EFI_ERROR (Status)) { - goto ReleaseToUnplugApicIds; + goto ReleaseToUnplugSelector; } // @@ -472,6 +483,10 @@ ReleasePostSmmPen: SmbaseReleasePostSmmPen (mPostSmmPenAddress, SystemTable->BootServices); mPostSmmPenAddress = 0; +ReleaseToUnplugSelector: + gMmst->MmFreePool (mToUnplugSelector); + mToUnplugSelector = NULL; + ReleaseToUnplugApicIds: gMmst->MmFreePool (mToUnplugApicIds); mToUnplugApicIds = NULL; diff --git a/OvmfPkg/CpuHotplugSmm/QemuCpuhp.c b/OvmfPkg/CpuHotplugSmm/QemuCpuhp.c index 8d4a6693c8d6..36372a5e6193 100644 --- a/OvmfPkg/CpuHotplugSmm/QemuCpuhp.c +++ b/OvmfPkg/CpuHotplugSmm/QemuCpuhp.c @@ -164,6 +164,9 @@ QemuCpuhpWriteCommand ( @param[out] ToUnplugApicIds The APIC IDs of the CPUs that are about to be hot-unplugged. + @param[out] ToUnplugSelector The QEMU Selectors of the CPUs that are about to + be hot-unplugged. + @param[out] ToUnplugCount The number of filled-in APIC IDs in ToUnplugApicIds. @@ -187,6 +190,7 @@ QemuCpuhpCollectApicIds ( OUT APIC_ID *PluggedApicIds, OUT UINT32 *PluggedCount, OUT APIC_ID *ToUnplugApicIds, + OUT UINT32 *ToUnplugSelector, OUT UINT32 *ToUnplugCount ) { @@ -204,6 +208,7 @@ QemuCpuhpCollectApicIds ( UINT32 PendingSelector; UINT8 CpuStatus; APIC_ID *ExtendIds; + UINT32 *ExtendSel; UINT32 *ExtendCount; APIC_ID NewApicId; @@ -245,10 +250,10 @@ QemuCpuhpCollectApicIds ( if ((CpuStatus & QEMU_CPUHP_STAT_INSERT) != 0) { // // The "insert" event guarantees the "enabled" status; plus it excludes - // the "remove" event. + // the "fw_remove" event. // if ((CpuStatus & QEMU_CPUHP_STAT_ENABLED) == 0 || - (CpuStatus & QEMU_CPUHP_STAT_REMOVE) != 0) { + (CpuStatus & QEMU_CPUHP_STAT_FW_REMOVE) != 0) { DEBUG ((DEBUG_ERROR, "%a: CurrentSelector=%u CpuStatus=0x%x: " "inconsistent CPU status\n", __FUNCTION__, CurrentSelector, CpuStatus)); @@ -259,40 +264,69 @@ QemuCpuhpCollectApicIds ( CurrentSelector)); ExtendIds = PluggedApicIds; + ExtendSel = NULL; ExtendCount = PluggedCount; - } else if ((CpuStatus & QEMU_CPUHP_STAT_REMOVE) != 0) { - DEBUG ((DEBUG_VERBOSE, "%a: CurrentSelector=%u: remove\n", __FUNCTION__, - CurrentSelector)); + } else if ((CpuStatus & QEMU_CPUHP_STAT_FW_REMOVE) != 0) { + // + // "fw_remove" event guarantees "enabled". + // + if ((CpuStatus & QEMU_CPUHP_STAT_ENABLED) == 0) { + DEBUG ((DEBUG_ERROR, "%a: CurrentSelector=%u CpuStatus=0x%x: " + "inconsistent CPU status\n", __FUNCTION__, CurrentSelector, + CpuStatus)); + return EFI_PROTOCOL_ERROR; + } + + DEBUG ((DEBUG_VERBOSE, "%a: CurrentSelector=%u: fw_remove\n", + __FUNCTION__, CurrentSelector)); ExtendIds = ToUnplugApicIds; + ExtendSel = ToUnplugSelector; ExtendCount = ToUnplugCount; + } else if ((CpuStatus & QEMU_CPUHP_STAT_REMOVE) != 0) { + // + // Let the OSPM deal with the "remove" event. + // + DEBUG ((DEBUG_VERBOSE, "%a: CurrentSelector=%u: remove (ignored)\n", + __FUNCTION__, CurrentSelector)); + + ExtendIds = NULL; + ExtendSel = NULL; + ExtendCount = NULL; } else { DEBUG ((DEBUG_VERBOSE, "%a: CurrentSelector=%u: no event\n", __FUNCTION__, CurrentSelector)); break; } - // - // Save the APIC ID of the CPU with the pending event, to the corresponding - // APIC ID array. - // - if (*ExtendCount == ApicIdCount) { - DEBUG ((DEBUG_ERROR, "%a: APIC ID array too small\n", __FUNCTION__)); - return EFI_BUFFER_TOO_SMALL; - } - QemuCpuhpWriteCommand (MmCpuIo, QEMU_CPUHP_CMD_GET_ARCH_ID); - NewApicId = QemuCpuhpReadCommandData (MmCpuIo); - DEBUG ((DEBUG_VERBOSE, "%a: ApicId=" FMT_APIC_ID "\n", __FUNCTION__, - NewApicId)); - ExtendIds[(*ExtendCount)++] = NewApicId; + ASSERT ((ExtendIds == NULL) == (ExtendCount == NULL)); + if (ExtendIds != NULL) { + // + // Save the APIC ID of the CPU with the pending event, to the + // corresponding APIC ID array. + // For unplug events, also save the CurrentSelector. + // + if (*ExtendCount == ApicIdCount) { + DEBUG ((DEBUG_ERROR, "%a: APIC ID array too small\n", __FUNCTION__)); + return EFI_BUFFER_TOO_SMALL; + } + QemuCpuhpWriteCommand (MmCpuIo, QEMU_CPUHP_CMD_GET_ARCH_ID); + NewApicId = QemuCpuhpReadCommandData (MmCpuIo); + DEBUG ((DEBUG_VERBOSE, "%a: ApicId=" FMT_APIC_ID "\n", __FUNCTION__, + NewApicId)); + if (ExtendSel != NULL) { + ExtendSel[(*ExtendCount)] = CurrentSelector; + } + ExtendIds[(*ExtendCount)++] = NewApicId; - // - // We've processed the CPU with (known) pending events, but we must never - // clear events. Therefore we need to advance past this CPU manually; - // otherwise, QEMU_CPUHP_CMD_GET_PENDING would stick to the currently - // selected CPU. - // - CurrentSelector++; + // + // We've processed the CPU with (known) pending events, but we must never + // clear events. Therefore we need to advance past this CPU manually; + // otherwise, QEMU_CPUHP_CMD_GET_PENDING would stick to the currently + // selected CPU. + // + CurrentSelector++; + } } while (CurrentSelector < PossibleCpuCount); DEBUG ((DEBUG_VERBOSE, "%a: PluggedCount=%u ToUnplugCount=%u\n", -- 2.9.3