From patchwork Tue Jun 6 10:48:08 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Max Filippov X-Patchwork-Id: 9768503 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id BFD8060364 for ; Tue, 6 Jun 2017 10:49:12 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id B865323B23 for ; Tue, 6 Jun 2017 10:49:12 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id AC3182623D; Tue, 6 Jun 2017 10:49:12 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-6.3 required=2.0 tests=BAYES_00, DKIM_ADSP_CUSTOM_MED, DKIM_SIGNED, FREEMAIL_FROM, FROM_LOCAL_NOVOWEL, RCVD_IN_DNSWL_HI, T_DKIM_INVALID autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 1CC6523B23 for ; Tue, 6 Jun 2017 10:49:11 +0000 (UTC) Received: from localhost ([::1]:37471 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dIC2v-00069P-JY for patchwork-qemu-devel@patchwork.kernel.org; Tue, 06 Jun 2017 06:49:09 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:34111) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dIC2K-00069K-1D for qemu-devel@nongnu.org; Tue, 06 Jun 2017 06:48:33 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dIC2D-0004ht-Nz for qemu-devel@nongnu.org; Tue, 06 Jun 2017 06:48:32 -0400 Received: from mail-lf0-x241.google.com ([2a00:1450:4010:c07::241]:34468) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1dIC2D-0004hj-Ay for qemu-devel@nongnu.org; Tue, 06 Jun 2017 06:48:25 -0400 Received: by mail-lf0-x241.google.com with SMTP id o28so2985814lfk.1 for ; Tue, 06 Jun 2017 03:48:25 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id; bh=+2Te6pwTYR9/celYs0Q6y0fhxt6xn9L/2i1EDum0/qs=; b=OVpVyhkFBlJQ3bCLMGYxdbA0U0hnLGkJkL8tsdEE1CgCwuuhzHtgSqbE5hsw8NeGLF FCPIYwJZCoIYpBfCwacsDczaWCUHfutfDh6dawgb9miEBsvL+TJUYDt1Fp+plO5u1+Ba zfePa/hA1r9nRCdZPabaNpNw0lKNRtstYCuNEr4O2LGXcup36DFd7wnepM4ynioL5dRQ Wski4yfp2QbfAgiy3asZI0xBYl+i6eYQEpcUzhXSyAHarNCdBFvZs56FpnrYTrabD8d6 IXOph4WeMs1AJBxVlte9rzdraWLBgMF+T6CnTlpcKVF2b98Jrhn8LwYnTihg5BUBOGpv /pzA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id; bh=+2Te6pwTYR9/celYs0Q6y0fhxt6xn9L/2i1EDum0/qs=; b=CqeQZjUSaPLC9l0YE4Da9/szhyhGhUf7spKH7tdphJCkwPJT789kW3J79u0Qxqk68R u+9utNrbd8YqtjSnuqaPq1CJlMtnK5iAI6ElPCbrk3rzPW6chfm6X7eLUaE95d+gZ/Og WMaHrnHs9iFa93mv7oHbr5R3jQhTvDKG8qCCLb+A73N6wbVBuMblR7v5nh0X/GJGeAo2 veRdmYSCGcdJV2UyPl560xdTE6MwqhaqTqEB9w/+VAdX3v0MeThjpxfKpt0v7GWfbntB GEHp4KOd8VqBrYLZTxUDN6js+e1DkadN05fwrLTSLnlGK3BI3H6Sgr260f4n6KLO8gbL Zf8w== X-Gm-Message-State: AODbwcB12rQBXhMZnuk4KsulZmPxso19p5/VyuxxaibzzZUzLFCQra3s +DoS1e6zs4Kcer3o X-Received: by 10.46.20.5 with SMTP id u5mr6590405ljd.66.1496746103489; Tue, 06 Jun 2017 03:48:23 -0700 (PDT) Received: from octofox.net ([5.19.183.212]) by smtp.gmail.com with ESMTPSA id n9sm7413512lfb.57.2017.06.06.03.48.21 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Tue, 06 Jun 2017 03:48:22 -0700 (PDT) From: Max Filippov To: qemu-devel@nongnu.org Date: Tue, 6 Jun 2017 03:48:08 -0700 Message-Id: <1496746088-31960-1-git-send-email-jcmvbkbc@gmail.com> X-Mailer: git-send-email 2.1.4 X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2a00:1450:4010:c07::241 Subject: [Qemu-devel] [PATCH v2] target/xtensa: support output to chardev console X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Max Filippov Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP In semihosting mode QEMU allows guest to read and write host file descriptors directly, including descriptors 0..2, a.k.a. stdin, stdout and stderr. Sometimes it's desirable to have semihosting console controlled by -serial option, e.g. to connect it to network. Add semihosting console to xtensa-semi.c, open it in the 'sim' machine in the presence of -serial option and direct stdout and stderr to it when it's present. Signed-off-by: Max Filippov --- Changes v1->v2: - include chardev/char-fe.h instead of sysemu/char.h hw/xtensa/sim.c | 4 +++ target/xtensa/cpu.h | 1 + target/xtensa/xtensa-semi.c | 66 +++++++++++++++++++++++++++++++++++---------- 3 files changed, 57 insertions(+), 14 deletions(-) diff --git a/hw/xtensa/sim.c b/hw/xtensa/sim.c index b27e28d..5521e91 100644 --- a/hw/xtensa/sim.c +++ b/hw/xtensa/sim.c @@ -114,6 +114,9 @@ static void xtensa_sim_init(MachineState *machine) xtensa_create_memory_regions(&sysram, "xtensa.sysram"); } + if (serial_hds[0]) { + xtensa_sim_open_console(serial_hds[0]); + } if (kernel_filename) { uint64_t elf_entry; uint64_t elf_lowaddr; @@ -136,6 +139,7 @@ static void xtensa_sim_machine_init(MachineClass *mc) mc->is_default = true; mc->init = xtensa_sim_init; mc->max_cpus = 4; + mc->no_serial = 1; } DEFINE_MACHINE("sim", xtensa_sim_machine_init) diff --git a/target/xtensa/cpu.h b/target/xtensa/cpu.h index ecca17d..ee29fb1 100644 --- a/target/xtensa/cpu.h +++ b/target/xtensa/cpu.h @@ -483,6 +483,7 @@ void xtensa_translate_init(void); void xtensa_breakpoint_handler(CPUState *cs); void xtensa_finalize_config(XtensaConfig *config); void xtensa_register_core(XtensaConfigList *node); +void xtensa_sim_open_console(Chardev *chr); void check_interrupts(CPUXtensaState *s); void xtensa_irq_init(CPUXtensaState *env); void *xtensa_get_extint(CPUXtensaState *env, unsigned extint); diff --git a/target/xtensa/xtensa-semi.c b/target/xtensa/xtensa-semi.c index ffcaf8d..32e2bd7 100644 --- a/target/xtensa/xtensa-semi.c +++ b/target/xtensa/xtensa-semi.c @@ -27,9 +27,14 @@ #include "qemu/osdep.h" #include "cpu.h" +#include "chardev/char-fe.h" #include "exec/helper-proto.h" #include "exec/semihost.h" +#include "qapi/error.h" #include "qemu/log.h" +#include "sysemu/sysemu.h" + +static CharBackend *xtensa_sim_console; enum { TARGET_SYS_exit = 1, @@ -148,6 +153,15 @@ static uint32_t errno_h2g(int host_errno) } } +void xtensa_sim_open_console(Chardev *chr) +{ + static CharBackend console; + + qemu_chr_fe_init(&console, chr, &error_abort); + qemu_chr_fe_set_handlers(&console, NULL, NULL, NULL, NULL, NULL, true); + xtensa_sim_console = &console; +} + void HELPER(simcall)(CPUXtensaState *env) { CPUState *cs = CPU(xtensa_env_get_cpu(env)); @@ -181,10 +195,25 @@ void HELPER(simcall)(CPUXtensaState *env) if (buf) { vaddr += io_sz; len -= io_sz; - io_done = is_write ? - write(fd, buf, io_sz) : - read(fd, buf, io_sz); - regs[3] = errno_h2g(errno); + if (fd < 3 && xtensa_sim_console) { + if (is_write && (fd == 1 || fd == 2)) { + io_done = qemu_chr_fe_write_all(xtensa_sim_console, + buf, io_sz); + regs[3] = errno_h2g(errno); + } else { + qemu_log_mask(LOG_GUEST_ERROR, + "%s fd %d is not supported with chardev console\n", + is_write ? + "writing to" : "reading from", fd); + io_done = -1; + regs[3] = TARGET_EBADF; + } + } else { + io_done = is_write ? + write(fd, buf, io_sz) : + read(fd, buf, io_sz); + regs[3] = errno_h2g(errno); + } if (io_done == -1) { error = true; io_done = 0; @@ -256,10 +285,6 @@ void HELPER(simcall)(CPUXtensaState *env) uint32_t target_tvv[2]; struct timeval tv = {0}; - fd_set fdset; - - FD_ZERO(&fdset); - FD_SET(fd, &fdset); if (target_tv) { cpu_memory_rw_debug(cs, target_tv, @@ -267,12 +292,25 @@ void HELPER(simcall)(CPUXtensaState *env) tv.tv_sec = (int32_t)tswap32(target_tvv[0]); tv.tv_usec = (int32_t)tswap32(target_tvv[1]); } - regs[2] = select(fd + 1, - rq == SELECT_ONE_READ ? &fdset : NULL, - rq == SELECT_ONE_WRITE ? &fdset : NULL, - rq == SELECT_ONE_EXCEPT ? &fdset : NULL, - target_tv ? &tv : NULL); - regs[3] = errno_h2g(errno); + if (fd < 3 && xtensa_sim_console) { + if ((fd == 1 || fd == 2) && rq == SELECT_ONE_WRITE) { + regs[2] = 1; + } else { + regs[2] = 0; + } + regs[3] = 0; + } else { + fd_set fdset; + + FD_ZERO(&fdset); + FD_SET(fd, &fdset); + regs[2] = select(fd + 1, + rq == SELECT_ONE_READ ? &fdset : NULL, + rq == SELECT_ONE_WRITE ? &fdset : NULL, + rq == SELECT_ONE_EXCEPT ? &fdset : NULL, + target_tv ? &tv : NULL); + regs[3] = errno_h2g(errno); + } } break;