111794Sbrandon.potter@amd.com/*
211794Sbrandon.potter@amd.com * Copyright (c) 2016 Advanced Micro Devices, Inc.
311794Sbrandon.potter@amd.com * Copyright (c) 2003-2005 The Regents of The University of Michigan
411794Sbrandon.potter@amd.com * All rights reserved.
511794Sbrandon.potter@amd.com *
611794Sbrandon.potter@amd.com * Redistribution and use in source and binary forms, with or without
711794Sbrandon.potter@amd.com * modification, are permitted provided that the following conditions are
811794Sbrandon.potter@amd.com * met: redistributions of source code must retain the above copyright
911794Sbrandon.potter@amd.com * notice, this list of conditions and the following disclaimer;
1011794Sbrandon.potter@amd.com * redistributions in binary form must reproduce the above copyright
1111794Sbrandon.potter@amd.com * notice, this list of conditions and the following disclaimer in the
1211794Sbrandon.potter@amd.com * documentation and/or other materials provided with the distribution;
1311794Sbrandon.potter@amd.com * neither the name of the copyright holders nor the names of its
1411794Sbrandon.potter@amd.com * contributors may be used to endorse or promote products derived from
1511794Sbrandon.potter@amd.com * this software without specific prior written permission.
1611794Sbrandon.potter@amd.com *
1711794Sbrandon.potter@amd.com * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
1811794Sbrandon.potter@amd.com * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
1911794Sbrandon.potter@amd.com * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
2011794Sbrandon.potter@amd.com * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
2111794Sbrandon.potter@amd.com * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
2211794Sbrandon.potter@amd.com * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
2311794Sbrandon.potter@amd.com * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
2411794Sbrandon.potter@amd.com * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
2511794Sbrandon.potter@amd.com * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
2611794Sbrandon.potter@amd.com * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
2711794Sbrandon.potter@amd.com * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
2811794Sbrandon.potter@amd.com *
2911794Sbrandon.potter@amd.com * Authors: Steve Reinhardt
3011794Sbrandon.potter@amd.com *          Ali Saidi
3111794Sbrandon.potter@amd.com *          Brandon Potter
3211794Sbrandon.potter@amd.com */
3311794Sbrandon.potter@amd.com
3411794Sbrandon.potter@amd.com#include "sim/syscall_desc.hh"
3511794Sbrandon.potter@amd.com
3611877Sbrandon.potter@amd.com#include <memory>
3711877Sbrandon.potter@amd.com
3811794Sbrandon.potter@amd.com#include "base/trace.hh"
3911877Sbrandon.potter@amd.com#include "base/types.hh"
4011794Sbrandon.potter@amd.com#include "config/the_isa.hh"
4111794Sbrandon.potter@amd.com#include "cpu/base.hh"
4211794Sbrandon.potter@amd.com#include "cpu/thread_context.hh"
4311877Sbrandon.potter@amd.com#include "sim/faults.hh"
4411794Sbrandon.potter@amd.com#include "sim/process.hh"
4511794Sbrandon.potter@amd.com#include "sim/syscall_debug_macros.hh"
4611794Sbrandon.potter@amd.com#include "sim/syscall_return.hh"
4711794Sbrandon.potter@amd.com
4811794Sbrandon.potter@amd.comvoid
4913995Sbrandon.potter@amd.comSyscallDesc::doSyscall(int callnum, ThreadContext *tc, Fault *fault)
5011794Sbrandon.potter@amd.com{
5113557Sgabeblack@google.com    RegVal arg[6] M5_VAR_USED;
5213995Sbrandon.potter@amd.com    auto process = tc->getProcessPtr();
5311794Sbrandon.potter@amd.com
5411794Sbrandon.potter@amd.com    /**
5511794Sbrandon.potter@amd.com     * Step through the first six parameters for the system call and
5611794Sbrandon.potter@amd.com     * retrieve their values. Note that index is incremented as a
5711994Salexandru.dutu@amd.com     * side-effect of the getSyscallArg method.
5811794Sbrandon.potter@amd.com     */
5911994Salexandru.dutu@amd.com    int index = 0;
6011994Salexandru.dutu@amd.com    for (int i = 0; i < 6; i++)
6111994Salexandru.dutu@amd.com        arg[i] = process->getSyscallArg(tc, index);
6211794Sbrandon.potter@amd.com
6311794Sbrandon.potter@amd.com    /**
6411794Sbrandon.potter@amd.com     * Linux supports up to six system call arguments through registers
6511794Sbrandon.potter@amd.com     * so we want to print all six. Check to the relevant man page to
6611794Sbrandon.potter@amd.com     * verify how many are actually used by a given system call.
6711794Sbrandon.potter@amd.com     */
6811794Sbrandon.potter@amd.com    DPRINTF_SYSCALL(Base, "%s called w/arguments %d, %d, %d, %d, %d, %d\n",
6911794Sbrandon.potter@amd.com                    _name, arg[0], arg[1], arg[2], arg[3], arg[4], arg[5]);
7011794Sbrandon.potter@amd.com
7111794Sbrandon.potter@amd.com    /** Invoke the system call */
7213995Sbrandon.potter@amd.com    SyscallReturn retval = (*executor)(this, callnum, tc);
7311794Sbrandon.potter@amd.com
7411794Sbrandon.potter@amd.com    /**
7511794Sbrandon.potter@amd.com     * If the system call needs to be restarted, most likely due to
7611794Sbrandon.potter@amd.com     * blocking behavior, warn that the system call will retry;
7711794Sbrandon.potter@amd.com     * alternatively, print the return value.
7811794Sbrandon.potter@amd.com     */
7911877Sbrandon.potter@amd.com    if (retval.needsRetry()) {
8011877Sbrandon.potter@amd.com        *fault = std::make_shared<SyscallRetryFault>();
8111794Sbrandon.potter@amd.com        DPRINTF_SYSCALL(Base, "%s needs retry\n", _name);
8211877Sbrandon.potter@amd.com    } else
8311794Sbrandon.potter@amd.com        DPRINTF_SYSCALL(Base, "%s returns %d\n", _name, retval.encodedValue());
8411794Sbrandon.potter@amd.com
8511794Sbrandon.potter@amd.com    if (!(_flags & SyscallDesc::SuppressReturnValue) && !retval.needsRetry())
8611794Sbrandon.potter@amd.com        process->setSyscallReturn(tc, retval);
8711794Sbrandon.potter@amd.com}
8811794Sbrandon.potter@amd.com
8911794Sbrandon.potter@amd.combool
9011794Sbrandon.potter@amd.comSyscallDesc::needWarning()
9111794Sbrandon.potter@amd.com{
9211794Sbrandon.potter@amd.com    bool suppress_warning = warnOnce() && _warned;
9311794Sbrandon.potter@amd.com    _warned = true;
9411794Sbrandon.potter@amd.com    return !suppress_warning;
9511794Sbrandon.potter@amd.com}
96