From owner-svn-src-all@FreeBSD.ORG Fri Dec 27 07:01:43 2013 Return-Path: Delivered-To: svn-src-all@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:1900:2254:206a::19:1]) (using TLSv1 with cipher ADH-AES256-SHA (256/256 bits)) (No client certificate requested) by hub.freebsd.org (Postfix) with ESMTPS id 89466E44; Fri, 27 Dec 2013 07:01:43 +0000 (UTC) Received: from svn.freebsd.org (svn.freebsd.org [IPv6:2001:1900:2254:2068::e6a:0]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mx1.freebsd.org (Postfix) with ESMTPS id 756E41653; Fri, 27 Dec 2013 07:01:43 +0000 (UTC) Received: from svn.freebsd.org ([127.0.1.70]) by svn.freebsd.org (8.14.7/8.14.7) with ESMTP id rBR71h7r098788; Fri, 27 Dec 2013 07:01:43 GMT (envelope-from neel@svn.freebsd.org) Received: (from neel@localhost) by svn.freebsd.org (8.14.7/8.14.7/Submit) id rBR71gtN098784; Fri, 27 Dec 2013 07:01:42 GMT (envelope-from neel@svn.freebsd.org) Message-Id: <201312270701.rBR71gtN098784@svn.freebsd.org> From: Neel Natu Date: Fri, 27 Dec 2013 07:01:42 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r259937 - head/sys/amd64/vmm/io X-SVN-Group: head MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-BeenThere: svn-src-all@freebsd.org X-Mailman-Version: 2.1.17 Precedence: list List-Id: "SVN commit messages for the entire src tree \(except for " user" and " projects" \)" List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Fri, 27 Dec 2013 07:01:43 -0000 Author: neel Date: Fri Dec 27 07:01:42 2013 New Revision: 259937 URL: http://svnweb.freebsd.org/changeset/base/259937 Log: Modify handling of write to the vlapic SVR register. The handler is now called after the register value is updated in the virtual APIC page. This will make it easier to handle APIC-write VM-exits with APIC register virtualization turned on. Additionally, mask all the LVT entries when the vlapic is software-disabled. Modified: head/sys/amd64/vmm/io/vlapic.c head/sys/amd64/vmm/io/vlapic.h head/sys/amd64/vmm/io/vlapic_priv.h Modified: head/sys/amd64/vmm/io/vlapic.c ============================================================================== --- head/sys/amd64/vmm/io/vlapic.c Fri Dec 27 05:01:13 2013 (r259936) +++ head/sys/amd64/vmm/io/vlapic.c Fri Dec 27 07:01:42 2013 (r259937) @@ -218,13 +218,17 @@ vlapic_timer_divisor(uint32_t dcr) } static void -vlapic_mask_lvts(uint32_t *lvts, int num_lvt) +vlapic_mask_lvts(struct vlapic *vlapic) { - int i; - for (i = 0; i < num_lvt; i++) { - *lvts |= APIC_LVT_M; - lvts += 4; - } + struct LAPIC *lapic = vlapic->apic_page; + + lapic->lvt_cmci |= APIC_LVT_M; + lapic->lvt_timer |= APIC_LVT_M; + lapic->lvt_thermal |= APIC_LVT_M; + lapic->lvt_pcint |= APIC_LVT_M; + lapic->lvt_lint0 |= APIC_LVT_M; + lapic->lvt_lint1 |= APIC_LVT_M; + lapic->lvt_error |= APIC_LVT_M; } #if 0 @@ -318,14 +322,15 @@ vlapic_reset(struct vlapic *vlapic) lapic->version |= (VLAPIC_MAXLVT_ENTRIES << MAXLVTSHIFT); lapic->dfr = 0xffffffff; lapic->svr = APIC_SVR_VECTOR; - vlapic_mask_lvts(&lapic->lvt_timer, 6); - vlapic_mask_lvts(&lapic->lvt_cmci, 1); + vlapic_mask_lvts(vlapic); vlapic_set_dcr(vlapic, 0); if (vlapic->vcpuid == 0) vlapic->boot_state = BS_RUNNING; /* BSP */ else vlapic->boot_state = BS_INIT; /* AP */ + + vlapic->svr_last = lapic->svr; } void @@ -1052,24 +1057,30 @@ vlapic_intr_accepted(struct vlapic *vlap vlapic_update_ppr(vlapic); } -static void -lapic_set_svr(struct vlapic *vlapic, uint32_t new) +void +vlapic_svr_write_handler(struct vlapic *vlapic) { struct LAPIC *lapic; - uint32_t old, changed; + uint32_t old, new, changed; lapic = vlapic->apic_page; - old = lapic->svr; + + new = lapic->svr; + old = vlapic->svr_last; + vlapic->svr_last = new; + changed = old ^ new; if ((changed & APIC_SVR_ENABLE) != 0) { if ((new & APIC_SVR_ENABLE) == 0) { /* - * The apic is now disabled so stop the apic timer. + * The apic is now disabled so stop the apic timer + * and mask all the LVT entries. */ VLAPIC_CTR0(vlapic, "vlapic is software-disabled"); VLAPIC_TIMER_LOCK(vlapic); callout_stop(&vlapic->callout); VLAPIC_TIMER_UNLOCK(vlapic); + vlapic_mask_lvts(vlapic); } else { /* * The apic is now enabled so restart the apic timer @@ -1080,7 +1091,6 @@ lapic_set_svr(struct vlapic *vlapic, uin vlapic_set_icr_timer(vlapic, lapic->icr_timer); } } - lapic->svr = new; } int @@ -1210,7 +1220,8 @@ vlapic_write(struct vlapic *vlapic, uint vlapic_dfr_write_handler(vlapic); break; case APIC_OFFSET_SVR: - lapic_set_svr(vlapic, data); + lapic->svr = data; + vlapic_svr_write_handler(vlapic); break; case APIC_OFFSET_ICR_LOW: if (!x2apic(vlapic)) { Modified: head/sys/amd64/vmm/io/vlapic.h ============================================================================== --- head/sys/amd64/vmm/io/vlapic.h Fri Dec 27 05:01:13 2013 (r259936) +++ head/sys/amd64/vmm/io/vlapic.h Fri Dec 27 07:01:42 2013 (r259937) @@ -75,4 +75,5 @@ void vlapic_post_intr(struct vlapic *vla void vlapic_id_write_handler(struct vlapic *vlapic); void vlapic_ldr_write_handler(struct vlapic *vlapic); void vlapic_dfr_write_handler(struct vlapic *vlapic); +void vlapic_svr_write_handler(struct vlapic *vlapic); #endif /* _VLAPIC_H_ */ Modified: head/sys/amd64/vmm/io/vlapic_priv.h ============================================================================== --- head/sys/amd64/vmm/io/vlapic_priv.h Fri Dec 27 05:01:13 2013 (r259936) +++ head/sys/amd64/vmm/io/vlapic_priv.h Fri Dec 27 07:01:42 2013 (r259937) @@ -116,6 +116,7 @@ struct vlapic { uint64_t msr_apicbase; enum boot_state boot_state; + uint32_t svr_last; }; void vlapic_init(struct vlapic *vlapic);