kernel_stats.cc revision 5568
14486Sbinkertn@umich.edu/* 24486Sbinkertn@umich.edu * Copyright (c) 2004-2005 The Regents of The University of Michigan 34486Sbinkertn@umich.edu * All rights reserved. 44486Sbinkertn@umich.edu * 54486Sbinkertn@umich.edu * Redistribution and use in source and binary forms, with or without 64486Sbinkertn@umich.edu * modification, are permitted provided that the following conditions are 74486Sbinkertn@umich.edu * met: redistributions of source code must retain the above copyright 84486Sbinkertn@umich.edu * notice, this list of conditions and the following disclaimer; 94486Sbinkertn@umich.edu * redistributions in binary form must reproduce the above copyright 104486Sbinkertn@umich.edu * notice, this list of conditions and the following disclaimer in the 114486Sbinkertn@umich.edu * documentation and/or other materials provided with the distribution; 124486Sbinkertn@umich.edu * neither the name of the copyright holders nor the names of its 134486Sbinkertn@umich.edu * contributors may be used to endorse or promote products derived from 144486Sbinkertn@umich.edu * this software without specific prior written permission. 154486Sbinkertn@umich.edu * 164486Sbinkertn@umich.edu * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 174486Sbinkertn@umich.edu * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 184486Sbinkertn@umich.edu * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 194486Sbinkertn@umich.edu * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 204486Sbinkertn@umich.edu * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 214486Sbinkertn@umich.edu * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 224486Sbinkertn@umich.edu * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 234486Sbinkertn@umich.edu * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 244486Sbinkertn@umich.edu * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 254486Sbinkertn@umich.edu * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 264486Sbinkertn@umich.edu * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 274486Sbinkertn@umich.edu * 284486Sbinkertn@umich.edu * Authors: Lisa Hsu 293102SN/A * Nathan Binkert 303102SN/A */ 315480Snate@binkert.org 325480Snate@binkert.org#include <map> 333812SN/A#include <stack> 345480Snate@binkert.org#include <string> 351310SN/A 362916SN/A#include "arch/alpha/linux/threadinfo.hh" 371310SN/A#include "arch/alpha/kernel_stats.hh" 382542SN/A#include "arch/alpha/osfpal.hh" 391366SN/A#include "base/trace.hh" 409338SAndreas.Sandberg@arm.com#include "cpu/thread_context.hh" 411692SN/A#include "kern/tru64/tru64_syscalls.hh" 421310SN/A#include "sim/system.hh" 432542SN/A 441366SN/Ausing namespace std; 459338SAndreas.Sandberg@arm.comusing namespace Stats; 463934SN/A 473885SN/Anamespace AlphaISA { 483932SN/Anamespace Kernel { 493932SN/A 501692SN/Aconst char *modestr[] = { "kernel", "user", "idle" }; 511634SN/A 521310SN/AStatistics::Statistics(System *system) 532542SN/A : ::Kernel::Statistics(system), 541366SN/A idleProcess((Addr)-1), themode(kernel), lastModeTick(0) 559338SAndreas.Sandberg@arm.com{ 561692SN/A} 572916SN/A 582916SN/Avoid 592916SN/AStatistics::regStats(const string &_name) 609338SAndreas.Sandberg@arm.com{ 612916SN/A ::Kernel::Statistics::regStats(_name); 622916SN/A 632916SN/A _callpal 642916SN/A .init(256) 652916SN/A .name(name() + ".callpal") 662916SN/A .desc("number of callpals executed") 672916SN/A .flags(total | pdf | nozero | nonan) 682916SN/A ; 692916SN/A 702916SN/A for (int i = 0; i < PAL::NumCodes; ++i) { 712916SN/A const char *str = PAL::name(i); 722916SN/A if (str) 733847SN/A _callpal.subname(i, str); 742916SN/A } 752916SN/A 762916SN/A _hwrei 772916SN/A .name(name() + ".inst.hwrei") 782916SN/A .desc("number of hwrei instructions executed") 792916SN/A ; 802916SN/A 812916SN/A _mode 822916SN/A .init(cpu_mode_num) 832916SN/A .name(name() + ".mode_switch") 842916SN/A .desc("number of protection mode switches") 852916SN/A ; 862916SN/A 872916SN/A for (int i = 0; i < cpu_mode_num; ++i) 882916SN/A _mode.subname(i, modestr[i]); 892916SN/A 902916SN/A _modeGood 912916SN/A .init(cpu_mode_num) 922916SN/A .name(name() + ".mode_good") 932916SN/A ; 945480Snate@binkert.org 952916SN/A for (int i = 0; i < cpu_mode_num; ++i) 962916SN/A _modeGood.subname(i, modestr[i]); 972916SN/A 982916SN/A _modeFraction 992916SN/A .name(name() + ".mode_switch_good") 1008839Sandreas.hansson@arm.com .desc("fraction of useful protection mode switches") 1018839Sandreas.hansson@arm.com .flags(total) 1022916SN/A ; 1037523Ssteve.reinhardt@amd.com 1048839Sandreas.hansson@arm.com for (int i = 0; i < cpu_mode_num; ++i) 1058839Sandreas.hansson@arm.com _modeFraction.subname(i, modestr[i]); 1068839Sandreas.hansson@arm.com 1078839Sandreas.hansson@arm.com _modeFraction = _modeGood / _mode; 1088839Sandreas.hansson@arm.com 1098839Sandreas.hansson@arm.com _modeTicks 1108839Sandreas.hansson@arm.com .init(cpu_mode_num) 1118839Sandreas.hansson@arm.com .name(name() + ".mode_ticks") 1128839Sandreas.hansson@arm.com .desc("number of ticks spent at the given mode") 1138839Sandreas.hansson@arm.com .flags(pdf) 1148839Sandreas.hansson@arm.com ; 1158839Sandreas.hansson@arm.com for (int i = 0; i < cpu_mode_num; ++i) 1168839Sandreas.hansson@arm.com _modeTicks.subname(i, modestr[i]); 1178839Sandreas.hansson@arm.com 1188839Sandreas.hansson@arm.com _swap_context 1198839Sandreas.hansson@arm.com .name(name() + ".swap_context") 1208839Sandreas.hansson@arm.com .desc("number of times the context was actually changed") 1218839Sandreas.hansson@arm.com ; 1228839Sandreas.hansson@arm.com} 1238839Sandreas.hansson@arm.com 1248839Sandreas.hansson@arm.comvoid 1258839Sandreas.hansson@arm.comStatistics::setIdleProcess(Addr idlepcbb, ThreadContext *tc) 1268839Sandreas.hansson@arm.com{ 127 assert(themode == kernel); 128 idleProcess = idlepcbb; 129 themode = idle; 130 changeMode(themode, tc); 131} 132 133void 134Statistics::changeMode(cpu_mode newmode, ThreadContext *tc) 135{ 136 _mode[newmode]++; 137 138 if (newmode == themode) 139 return; 140 141 DPRINTF(Context, "old mode=%s new mode=%s pid=%d\n", 142 modestr[themode], modestr[newmode], 143 Linux::ThreadInfo(tc).curTaskPID()); 144 145 _modeGood[newmode]++; 146 _modeTicks[themode] += curTick - lastModeTick; 147 148 lastModeTick = curTick; 149 themode = newmode; 150} 151 152void 153Statistics::mode(cpu_mode newmode, ThreadContext *tc) 154{ 155 Addr pcbb = tc->readMiscRegNoEffect(IPR_PALtemp23); 156 157 if (newmode == kernel && pcbb == idleProcess) 158 newmode = idle; 159 160 changeMode(newmode, tc); 161} 162 163void 164Statistics::context(Addr oldpcbb, Addr newpcbb, ThreadContext *tc) 165{ 166 assert(themode != user); 167 168 _swap_context++; 169 changeMode(newpcbb == idleProcess ? idle : kernel, tc); 170 171 DPRINTF(Context, "Context Switch old pid=%d new pid=%d\n", 172 Linux::ThreadInfo(tc, oldpcbb).curTaskPID(), 173 Linux::ThreadInfo(tc, newpcbb).curTaskPID()); 174} 175 176void 177Statistics::callpal(int code, ThreadContext *tc) 178{ 179 if (!PAL::name(code)) 180 return; 181 182 _callpal[code]++; 183 184 switch (code) { 185 case PAL::callsys: { 186 int number = tc->readIntReg(0); 187 if (SystemCalls<Tru64>::validSyscallNumber(number)) { 188 int cvtnum = SystemCalls<Tru64>::convert(number); 189 _syscall[cvtnum]++; 190 } 191 } break; 192 } 193} 194 195void 196Statistics::serialize(ostream &os) 197{ 198 ::Kernel::Statistics::serialize(os); 199 int exemode = themode; 200 SERIALIZE_SCALAR(exemode); 201 SERIALIZE_SCALAR(idleProcess); 202 SERIALIZE_SCALAR(lastModeTick); 203} 204 205void 206Statistics::unserialize(Checkpoint *cp, const string §ion) 207{ 208 ::Kernel::Statistics::unserialize(cp, section); 209 int exemode; 210 UNSERIALIZE_SCALAR(exemode); 211 UNSERIALIZE_SCALAR(idleProcess); 212 UNSERIALIZE_SCALAR(lastModeTick); 213 themode = (cpu_mode)exemode; 214} 215 216} // namespace Kernel 217} // namespace AlphaISA 218