From patchwork Mon Nov 1 15:01:36 2010 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Alexander Graf X-Patchwork-Id: 69804 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from lists.gnu.org (lists.gnu.org [199.232.76.165]) (using TLSv1 with cipher DHE-RSA-AES256-SHA (256/256 bits)) (Client did not present a certificate) by ozlabs.org (Postfix) with ESMTPS id D6C221007D4 for ; Tue, 2 Nov 2010 03:12:58 +1100 (EST) Received: from localhost ([127.0.0.1]:58878 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.43) id 1PCx00-0001ET-NB for incoming@patchwork.ozlabs.org; Mon, 01 Nov 2010 12:12:44 -0400 Received: from [140.186.70.92] (port=52917 helo=eggs.gnu.org) by lists.gnu.org with esmtp (Exim 4.43) id 1PCvu1-0003jY-HI for qemu-devel@nongnu.org; Mon, 01 Nov 2010 11:02:45 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1PCvtX-0000h1-4l for qemu-devel@nongnu.org; Mon, 01 Nov 2010 11:02:05 -0400 Received: from cantor2.suse.de ([195.135.220.15]:39339 helo=mx2.suse.de) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1PCvtW-0000g7-Om for qemu-devel@nongnu.org; Mon, 01 Nov 2010 11:01:58 -0400 Received: from relay1.suse.de (charybdis-ext.suse.de [195.135.221.2]) by mx2.suse.de (Postfix) with ESMTP id 69A9689FC6; Mon, 1 Nov 2010 16:01:54 +0100 (CET) From: Alexander Graf To: qemu-devel Developers Date: Mon, 1 Nov 2010 16:01:36 +0100 Message-Id: <1288623713-28062-24-git-send-email-agraf@suse.de> X-Mailer: git-send-email 1.6.0.2 In-Reply-To: <1288623713-28062-1-git-send-email-agraf@suse.de> References: <1288623713-28062-1-git-send-email-agraf@suse.de> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.4-2.6 Cc: Gerd Hoffmann Subject: [Qemu-devel] [PATCH 23/40] xenner: kernel: generic MM functionality X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: qemu-devel.nongnu.org List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Sender: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Xenner does its own memory management bookkeeping which can be kept platform agnostic. This patch adds that. Signed-off-by: Alexander Graf --- pc-bios/xenner/xenner-mm.c | 105 ++++++++++++++++++++++++++++++++++++++++++++ 1 files changed, 105 insertions(+), 0 deletions(-) create mode 100644 pc-bios/xenner/xenner-mm.c diff --git a/pc-bios/xenner/xenner-mm.c b/pc-bios/xenner/xenner-mm.c new file mode 100644 index 0000000..ccbd48a --- /dev/null +++ b/pc-bios/xenner/xenner-mm.c @@ -0,0 +1,105 @@ +/* + * Copyright (C) Red Hat 2007 + * Copyright (C) Novell Inc. 2010 + * + * Author(s): Gerd Hoffmann + * Alexander Graf + * + * Xenner generic memory management + * + * 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; under version 2 of the License. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, see . + */ + +static int heap_type = HEAP_EMU; +static void *heap_emu = NULL; +static void *heap_high_start = NULL; +static void *heap_high = NULL; + +unsigned long heap_size(void) +{ + unsigned long r = 0; + + switch (heap_type) { + case HEAP_EMU: + r = (unsigned long)heap_emu - (unsigned long)_vstop; + break; + case HEAP_HIGH: + r = (unsigned long)heap_high - (unsigned long)heap_high_start; + break; + } + + return r; +} + +void switch_heap(int _heap_type) +{ + if ((_heap_type == HEAP_HIGH) && !heap_high) { +#if defined(CONFIG_32BIT) + heap_high = (void*)(uintptr_t)XEN_IPT; +#elif defined(CONFIG_64BIT) + uintptr_t mfn_guest = emudev_get(EMUDEV_CONF_GUEST_START_PFN, 0); + uintptr_t init_pt_pfn = emudev_get(EMUDEV_CONF_PFN_INIT_PT, 0); + + heap_high = map_page(frame_to_addr(mfn_guest + init_pt_pfn)); +#endif + heap_high_start = heap_high; + } + + switch (_heap_type) { + case HEAP_EMU: + case HEAP_HIGH: + heap_type = _heap_type; + break; + } +} + +void *get_pages(int pages, const char *purpose) +{ + void **heap_cur = &heap_emu; + void *ptr; + + if (!heap_emu) { + heap_emu = _vstop; + } + + switch (heap_type) { + case HEAP_EMU: + heap_cur = &heap_emu; + break; + case HEAP_HIGH: + heap_cur = &heap_high; + break; + } + + ptr = *heap_cur; + *heap_cur += pages * PAGE_SIZE; + printk(2, "%s: %d page(s) at %p (for %s)\n", + __FUNCTION__, pages, ptr, purpose); + memset(ptr, 0, pages * PAGE_SIZE); + return ptr; +} + +void *get_memory(int bytes, const char *purpose) +{ + int pages = (bytes + PAGE_SIZE -1) / PAGE_SIZE; + return get_pages(pages, purpose); +} + +void paging_start(struct xen_cpu *cpu) +{ + ureg_t cr3_mfn; + + cr3_mfn = cpu->init_ctxt->ctrlreg[3] >> PAGE_SHIFT; + update_emu_mappings(cr3_mfn); + pv_write_cr3(cpu, cr3_mfn); +}