serialize.cc revision 7532
12SN/A/* 21762SN/A * Copyright (c) 2002-2005 The Regents of The University of Michigan 32SN/A * All rights reserved. 42SN/A * 52SN/A * Redistribution and use in source and binary forms, with or without 62SN/A * modification, are permitted provided that the following conditions are 72SN/A * met: redistributions of source code must retain the above copyright 82SN/A * notice, this list of conditions and the following disclaimer; 92SN/A * redistributions in binary form must reproduce the above copyright 102SN/A * notice, this list of conditions and the following disclaimer in the 112SN/A * documentation and/or other materials provided with the distribution; 122SN/A * neither the name of the copyright holders nor the names of its 132SN/A * contributors may be used to endorse or promote products derived from 142SN/A * this software without specific prior written permission. 152SN/A * 162SN/A * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 172SN/A * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 182SN/A * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 192SN/A * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 202SN/A * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 212SN/A * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 222SN/A * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 232SN/A * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 242SN/A * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 252SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 262SN/A * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 272665Ssaidi@eecs.umich.edu * 282760Sbinkertn@umich.edu * Authors: Nathan Binkert 292760Sbinkertn@umich.edu * Erik Hallnor 302665Ssaidi@eecs.umich.edu * Steve Reinhardt 312SN/A */ 322SN/A 332SN/A#include <sys/time.h> 34363SN/A#include <sys/types.h> 35363SN/A#include <sys/stat.h> 361354SN/A#include <errno.h> 372SN/A 382SN/A#include <fstream> 392SN/A#include <list> 402SN/A#include <string> 412SN/A#include <vector> 422SN/A 43363SN/A#include "base/inifile.hh" 4456SN/A#include "base/misc.hh" 451388SN/A#include "base/output.hh" 46217SN/A#include "base/str.hh" 47363SN/A#include "base/trace.hh" 4856SN/A#include "sim/eventq.hh" 4956SN/A#include "sim/serialize.hh" 5056SN/A#include "sim/sim_events.hh" 511638SN/A#include "sim/sim_exit.hh" 5256SN/A#include "sim/sim_object.hh" 532SN/A 542356SN/A// For stat reset hack 552356SN/A#include "sim/stat_control.hh" 562356SN/A 572SN/Ausing namespace std; 582SN/A 594000Ssaidi@eecs.umich.eduextern SimObject *resolveSimObject(const string &); 604000Ssaidi@eecs.umich.edu 614762Snate@binkert.org// 624762Snate@binkert.org// The base implementations use to_number for parsing and '<<' for 634762Snate@binkert.org// displaying, suitable for integer types. 644762Snate@binkert.org// 654762Snate@binkert.orgtemplate <class T> 664762Snate@binkert.orgbool 674762Snate@binkert.orgparseParam(const string &s, T &value) 684762Snate@binkert.org{ 694762Snate@binkert.org return to_number(s, value); 704762Snate@binkert.org} 714762Snate@binkert.org 724762Snate@binkert.orgtemplate <class T> 734762Snate@binkert.orgvoid 744762Snate@binkert.orgshowParam(ostream &os, const T &value) 754762Snate@binkert.org{ 764762Snate@binkert.org os << value; 774762Snate@binkert.org} 784762Snate@binkert.org 794762Snate@binkert.org// 804762Snate@binkert.org// Template specializations: 814762Snate@binkert.org// - char (8-bit integer) 824762Snate@binkert.org// - floating-point types 834762Snate@binkert.org// - bool 844762Snate@binkert.org// - string 854762Snate@binkert.org// 864762Snate@binkert.org 874762Snate@binkert.org// Treat 8-bit ints (chars) as ints on output, not as chars 884762Snate@binkert.orgtemplate <> 894762Snate@binkert.orgvoid 907494Ssteve.reinhardt@amd.comshowParam(ostream &os, const char &value) 917494Ssteve.reinhardt@amd.com{ 927494Ssteve.reinhardt@amd.com os << (int)value; 937494Ssteve.reinhardt@amd.com} 947494Ssteve.reinhardt@amd.com 957494Ssteve.reinhardt@amd.com 967494Ssteve.reinhardt@amd.comtemplate <> 977494Ssteve.reinhardt@amd.comvoid 987490Ssteve.reinhardt@amd.comshowParam(ostream &os, const signed char &value) 994762Snate@binkert.org{ 1004762Snate@binkert.org os << (int)value; 1014762Snate@binkert.org} 1024762Snate@binkert.org 1034762Snate@binkert.org 1044762Snate@binkert.orgtemplate <> 1054762Snate@binkert.orgvoid 1064762Snate@binkert.orgshowParam(ostream &os, const unsigned char &value) 1074762Snate@binkert.org{ 1084762Snate@binkert.org os << (unsigned int)value; 1094762Snate@binkert.org} 1104762Snate@binkert.org 1114762Snate@binkert.org 1124762Snate@binkert.org// Use sscanf() for FP types as to_number() only handles integers 1134762Snate@binkert.orgtemplate <> 1144762Snate@binkert.orgbool 1154762Snate@binkert.orgparseParam(const string &s, float &value) 1164762Snate@binkert.org{ 1174762Snate@binkert.org return (sscanf(s.c_str(), "%f", &value) == 1); 1184762Snate@binkert.org} 1194762Snate@binkert.org 1204762Snate@binkert.orgtemplate <> 1214762Snate@binkert.orgbool 1224762Snate@binkert.orgparseParam(const string &s, double &value) 1234762Snate@binkert.org{ 1244762Snate@binkert.org return (sscanf(s.c_str(), "%lf", &value) == 1); 1254762Snate@binkert.org} 1264762Snate@binkert.org 1274762Snate@binkert.orgtemplate <> 1284762Snate@binkert.orgbool 1294762Snate@binkert.orgparseParam(const string &s, bool &value) 1304762Snate@binkert.org{ 1314762Snate@binkert.org const string &ls = to_lower(s); 1324762Snate@binkert.org 1334762Snate@binkert.org if (ls == "true") { 1344762Snate@binkert.org value = true; 1354762Snate@binkert.org return true; 1364762Snate@binkert.org } 1374762Snate@binkert.org 1384762Snate@binkert.org if (ls == "false") { 1394762Snate@binkert.org value = false; 1404762Snate@binkert.org return true; 1414762Snate@binkert.org } 1424762Snate@binkert.org 1434762Snate@binkert.org return false; 1444762Snate@binkert.org} 1454762Snate@binkert.org 1464762Snate@binkert.org// Display bools as strings 1474762Snate@binkert.orgtemplate <> 1484762Snate@binkert.orgvoid 1494762Snate@binkert.orgshowParam(ostream &os, const bool &value) 1504762Snate@binkert.org{ 1514762Snate@binkert.org os << (value ? "true" : "false"); 1524762Snate@binkert.org} 1534762Snate@binkert.org 1544762Snate@binkert.org 1554762Snate@binkert.org// String requires no processing to speak of 1564762Snate@binkert.orgtemplate <> 1574762Snate@binkert.orgbool 1584762Snate@binkert.orgparseParam(const string &s, string &value) 1594762Snate@binkert.org{ 1604762Snate@binkert.org value = s; 1614762Snate@binkert.org return true; 1624762Snate@binkert.org} 1634762Snate@binkert.org 1642287SN/Aint Serializable::ckptMaxCount = 0; 1652287SN/Aint Serializable::ckptCount = 0; 1662287SN/Aint Serializable::ckptPrevCount = -1; 1671637SN/A 1682SN/Avoid 169395SN/ASerializable::nameOut(ostream &os) 1702SN/A{ 171217SN/A os << "\n[" << name() << "]\n"; 1722SN/A} 1732SN/A 1742SN/Avoid 175395SN/ASerializable::nameOut(ostream &os, const string &_name) 1762SN/A{ 177217SN/A os << "\n[" << _name << "]\n"; 1782SN/A} 1792SN/A 180217SN/Atemplate <class T> 1812SN/Avoid 1826225Snate@binkert.orgparamOut(ostream &os, const string &name, const T ¶m) 1832SN/A{ 184217SN/A os << name << "="; 185217SN/A showParam(os, param); 186217SN/A os << "\n"; 1872SN/A} 1882SN/A 1894841Ssaidi@eecs.umich.edutemplate <class T> 1904841Ssaidi@eecs.umich.eduvoid 1916225Snate@binkert.orgarrayParamOut(ostream &os, const string &name, const vector<T> ¶m) 1924841Ssaidi@eecs.umich.edu{ 1936227Snate@binkert.org typename vector<T>::size_type size = param.size(); 1944841Ssaidi@eecs.umich.edu os << name << "="; 1954841Ssaidi@eecs.umich.edu if (size > 0) 1964841Ssaidi@eecs.umich.edu showParam(os, param[0]); 1976227Snate@binkert.org for (typename vector<T>::size_type i = 1; i < size; ++i) { 1984841Ssaidi@eecs.umich.edu os << " "; 1994841Ssaidi@eecs.umich.edu showParam(os, param[i]); 2004841Ssaidi@eecs.umich.edu } 2014841Ssaidi@eecs.umich.edu os << "\n"; 2024841Ssaidi@eecs.umich.edu} 2034841Ssaidi@eecs.umich.edu 204217SN/A 205217SN/Atemplate <class T> 206217SN/Avoid 2076225Snate@binkert.orgparamIn(Checkpoint *cp, const string §ion, const string &name, T ¶m) 2082SN/A{ 2096225Snate@binkert.org string str; 210237SN/A if (!cp->find(section, name, str) || !parseParam(str, param)) { 211217SN/A fatal("Can't unserialize '%s:%s'\n", section, name); 212217SN/A } 2132SN/A} 2142SN/A 2156820SLisa.Hsu@amd.comtemplate <class T> 2166820SLisa.Hsu@amd.combool 2176820SLisa.Hsu@amd.comoptParamIn(Checkpoint *cp, const string §ion, const string &name, T ¶m) 2186820SLisa.Hsu@amd.com{ 2196820SLisa.Hsu@amd.com string str; 2206820SLisa.Hsu@amd.com if (!cp->find(section, name, str) || !parseParam(str, param)) { 2216820SLisa.Hsu@amd.com warn("optional parameter %s:%s not present\n", section, name); 2226820SLisa.Hsu@amd.com return false; 2236820SLisa.Hsu@amd.com } else { 2246820SLisa.Hsu@amd.com return true; 2256820SLisa.Hsu@amd.com } 2266820SLisa.Hsu@amd.com} 227217SN/A 228217SN/Atemplate <class T> 229217SN/Avoid 2306227Snate@binkert.orgarrayParamOut(ostream &os, const string &name, const T *param, unsigned size) 231217SN/A{ 232217SN/A os << name << "="; 233217SN/A if (size > 0) 234217SN/A showParam(os, param[0]); 2356227Snate@binkert.org for (unsigned i = 1; i < size; ++i) { 236217SN/A os << " "; 237217SN/A showParam(os, param[i]); 238217SN/A } 239217SN/A os << "\n"; 240217SN/A} 241217SN/A 242217SN/A 243217SN/Atemplate <class T> 244217SN/Avoid 2456225Snate@binkert.orgarrayParamIn(Checkpoint *cp, const string §ion, const string &name, 2466227Snate@binkert.org T *param, unsigned size) 247217SN/A{ 2486225Snate@binkert.org string str; 249237SN/A if (!cp->find(section, name, str)) { 250217SN/A fatal("Can't unserialize '%s:%s'\n", section, name); 251217SN/A } 252217SN/A 253217SN/A // code below stolen from VectorParam<T>::parse(). 254217SN/A // it would be nice to unify these somehow... 255217SN/A 256217SN/A vector<string> tokens; 257217SN/A 258217SN/A tokenize(tokens, str, ' '); 259217SN/A 260217SN/A // Need this if we were doing a vector 261217SN/A // value.resize(tokens.size()); 262217SN/A 263217SN/A if (tokens.size() != size) { 264217SN/A fatal("Array size mismatch on %s:%s'\n", section, name); 265217SN/A } 266217SN/A 2676227Snate@binkert.org for (vector<string>::size_type i = 0; i < tokens.size(); i++) { 268217SN/A // need to parse into local variable to handle vector<bool>, 269217SN/A // for which operator[] returns a special reference class 270217SN/A // that's not the same as 'bool&', (since it's a packed 271217SN/A // vector) 272217SN/A T scalar_value; 273217SN/A if (!parseParam(tokens[i], scalar_value)) { 274217SN/A string err("could not parse \""); 275217SN/A 276217SN/A err += str; 277217SN/A err += "\""; 278217SN/A 279217SN/A fatal(err); 280217SN/A } 281217SN/A 282217SN/A // assign parsed value to vector 283217SN/A param[i] = scalar_value; 284217SN/A } 285217SN/A} 286217SN/A 2874841Ssaidi@eecs.umich.edutemplate <class T> 2884841Ssaidi@eecs.umich.eduvoid 2896225Snate@binkert.orgarrayParamIn(Checkpoint *cp, const string §ion, 2906225Snate@binkert.org const string &name, vector<T> ¶m) 2914841Ssaidi@eecs.umich.edu{ 2926225Snate@binkert.org string str; 2934841Ssaidi@eecs.umich.edu if (!cp->find(section, name, str)) { 2944841Ssaidi@eecs.umich.edu fatal("Can't unserialize '%s:%s'\n", section, name); 2954841Ssaidi@eecs.umich.edu } 2964841Ssaidi@eecs.umich.edu 2974841Ssaidi@eecs.umich.edu // code below stolen from VectorParam<T>::parse(). 2984841Ssaidi@eecs.umich.edu // it would be nice to unify these somehow... 2994841Ssaidi@eecs.umich.edu 3004841Ssaidi@eecs.umich.edu vector<string> tokens; 3014841Ssaidi@eecs.umich.edu 3024841Ssaidi@eecs.umich.edu tokenize(tokens, str, ' '); 3034841Ssaidi@eecs.umich.edu 3044841Ssaidi@eecs.umich.edu // Need this if we were doing a vector 3054841Ssaidi@eecs.umich.edu // value.resize(tokens.size()); 3064841Ssaidi@eecs.umich.edu 3074841Ssaidi@eecs.umich.edu param.resize(tokens.size()); 3084841Ssaidi@eecs.umich.edu 3096227Snate@binkert.org for (vector<string>::size_type i = 0; i < tokens.size(); i++) { 3104841Ssaidi@eecs.umich.edu // need to parse into local variable to handle vector<bool>, 3114841Ssaidi@eecs.umich.edu // for which operator[] returns a special reference class 3124841Ssaidi@eecs.umich.edu // that's not the same as 'bool&', (since it's a packed 3134841Ssaidi@eecs.umich.edu // vector) 3144841Ssaidi@eecs.umich.edu T scalar_value; 3154841Ssaidi@eecs.umich.edu if (!parseParam(tokens[i], scalar_value)) { 3164841Ssaidi@eecs.umich.edu string err("could not parse \""); 3174841Ssaidi@eecs.umich.edu 3184841Ssaidi@eecs.umich.edu err += str; 3194841Ssaidi@eecs.umich.edu err += "\""; 3204841Ssaidi@eecs.umich.edu 3214841Ssaidi@eecs.umich.edu fatal(err); 3224841Ssaidi@eecs.umich.edu } 3234841Ssaidi@eecs.umich.edu 3244841Ssaidi@eecs.umich.edu // assign parsed value to vector 3254841Ssaidi@eecs.umich.edu param[i] = scalar_value; 3264841Ssaidi@eecs.umich.edu } 3274841Ssaidi@eecs.umich.edu} 3284841Ssaidi@eecs.umich.edu 329237SN/Avoid 3306225Snate@binkert.orgobjParamIn(Checkpoint *cp, const string §ion, 3316225Snate@binkert.org const string &name, SimObject * ¶m) 332237SN/A{ 333237SN/A if (!cp->findObj(section, name, param)) { 334237SN/A fatal("Can't unserialize '%s:%s'\n", section, name); 335237SN/A } 336237SN/A} 337237SN/A 338237SN/A 3395543Ssaidi@eecs.umich.edu#define INSTANTIATE_PARAM_TEMPLATES(type) \ 3405543Ssaidi@eecs.umich.edutemplate void \ 3416225Snate@binkert.orgparamOut(ostream &os, const string &name, type const ¶m); \ 3425543Ssaidi@eecs.umich.edutemplate void \ 3436225Snate@binkert.orgparamIn(Checkpoint *cp, const string §ion, \ 3446225Snate@binkert.org const string &name, type & param); \ 3456820SLisa.Hsu@amd.comtemplate bool \ 3466820SLisa.Hsu@amd.comoptParamIn(Checkpoint *cp, const string §ion, \ 3476820SLisa.Hsu@amd.com const string &name, type & param); \ 3485543Ssaidi@eecs.umich.edutemplate void \ 3496225Snate@binkert.orgarrayParamOut(ostream &os, const string &name, \ 3506227Snate@binkert.org type const *param, unsigned size); \ 3515543Ssaidi@eecs.umich.edutemplate void \ 3526225Snate@binkert.orgarrayParamIn(Checkpoint *cp, const string §ion, \ 3536227Snate@binkert.org const string &name, type *param, unsigned size); \ 3545543Ssaidi@eecs.umich.edutemplate void \ 3556225Snate@binkert.orgarrayParamOut(ostream &os, const string &name, \ 3566225Snate@binkert.org const vector<type> ¶m); \ 3575543Ssaidi@eecs.umich.edutemplate void \ 3586225Snate@binkert.orgarrayParamIn(Checkpoint *cp, const string §ion, \ 3596225Snate@binkert.org const string &name, vector<type> ¶m); 360217SN/A 3617494Ssteve.reinhardt@amd.comINSTANTIATE_PARAM_TEMPLATES(char) 3621642SN/AINSTANTIATE_PARAM_TEMPLATES(signed char) 3631642SN/AINSTANTIATE_PARAM_TEMPLATES(unsigned char) 3641642SN/AINSTANTIATE_PARAM_TEMPLATES(signed short) 3651642SN/AINSTANTIATE_PARAM_TEMPLATES(unsigned short) 3661642SN/AINSTANTIATE_PARAM_TEMPLATES(signed int) 3671642SN/AINSTANTIATE_PARAM_TEMPLATES(unsigned int) 3681642SN/AINSTANTIATE_PARAM_TEMPLATES(signed long) 3691642SN/AINSTANTIATE_PARAM_TEMPLATES(unsigned long) 3701642SN/AINSTANTIATE_PARAM_TEMPLATES(signed long long) 3711642SN/AINSTANTIATE_PARAM_TEMPLATES(unsigned long long) 372219SN/AINSTANTIATE_PARAM_TEMPLATES(bool) 3735992Snate@binkert.orgINSTANTIATE_PARAM_TEMPLATES(float) 3745992Snate@binkert.orgINSTANTIATE_PARAM_TEMPLATES(double) 375217SN/AINSTANTIATE_PARAM_TEMPLATES(string) 376217SN/A 377217SN/A 378395SN/A///////////////////////////// 379395SN/A 380395SN/A/// Container for serializing global variables (not associated with 381395SN/A/// any serialized object). 382395SN/Aclass Globals : public Serializable 3832SN/A{ 384395SN/A public: 385512SN/A const string name() const; 386510SN/A void serialize(ostream &os); 387395SN/A void unserialize(Checkpoint *cp); 388395SN/A}; 3892SN/A 390395SN/A/// The one and only instance of the Globals class. 391395SN/AGlobals globals; 3922SN/A 393512SN/Aconst string 394395SN/AGlobals::name() const 3952SN/A{ 396395SN/A return "Globals"; 3972SN/A} 3982SN/A 3992SN/Avoid 400510SN/AGlobals::serialize(ostream &os) 4012SN/A{ 402395SN/A nameOut(os); 403395SN/A SERIALIZE_SCALAR(curTick); 404395SN/A 405395SN/A nameOut(os, "MainEventQueue"); 406395SN/A mainEventQueue.serialize(os); 4072SN/A} 4082SN/A 4092SN/Avoid 410395SN/AGlobals::unserialize(Checkpoint *cp) 4112SN/A{ 412395SN/A const string §ion = name(); 413395SN/A UNSERIALIZE_SCALAR(curTick); 4142SN/A 415395SN/A mainEventQueue.unserialize(cp, "MainEventQueue"); 4162SN/A} 4172SN/A 4185739Snate@binkert.orgSerializable::Serializable() 4195739Snate@binkert.org{ 4205739Snate@binkert.org} 4215739Snate@binkert.org 4225739Snate@binkert.orgSerializable::~Serializable() 4235739Snate@binkert.org{ 4245739Snate@binkert.org} 4255739Snate@binkert.org 4265739Snate@binkert.orgvoid 4276225Snate@binkert.orgSerializable::serialize(ostream &os) 4285739Snate@binkert.org{ 4295739Snate@binkert.org} 4305739Snate@binkert.org 4315739Snate@binkert.orgvoid 4326225Snate@binkert.orgSerializable::unserialize(Checkpoint *cp, const string §ion) 4335739Snate@binkert.org{ 4345739Snate@binkert.org} 4355739Snate@binkert.org 4362SN/Avoid 4376225Snate@binkert.orgSerializable::serializeAll(const string &cpt_dir) 4382SN/A{ 4397491Ssteve.reinhardt@amd.com string dir = Checkpoint::setDir(cpt_dir); 440363SN/A if (mkdir(dir.c_str(), 0775) == -1 && errno != EEXIST) 441449SN/A fatal("couldn't mkdir %s\n", dir); 442363SN/A 443449SN/A string cpt_file = dir + Checkpoint::baseFilename; 444395SN/A ofstream outstream(cpt_file.c_str()); 4452SN/A time_t t = time(NULL); 4465581Ssaidi@eecs.umich.edu if (!outstream.is_open()) 4475581Ssaidi@eecs.umich.edu fatal("Unable to open file %s for writing\n", cpt_file.c_str()); 4486818SLisa.Hsu@amd.com outstream << "## checkpoint generated: " << ctime(&t); 4492SN/A 450395SN/A globals.serialize(outstream); 451395SN/A SimObject::serializeAll(outstream); 452395SN/A} 4532SN/A 4542797Sktlim@umich.eduvoid 455395SN/ASerializable::unserializeGlobals(Checkpoint *cp) 456395SN/A{ 457395SN/A globals.unserialize(cp); 458395SN/A} 4592SN/A 4602SN/Avoid 4616225Snate@binkert.orgdebug_serialize(const string &cpt_dir) 4622SN/A{ 4632868Sktlim@umich.edu Serializable::serializeAll(cpt_dir); 4642SN/A} 4652SN/A 4662SN/A 4672SN/A//////////////////////////////////////////////////////////////////////// 4682SN/A// 469395SN/A// SerializableClass member definitions 4702SN/A// 4712SN/A//////////////////////////////////////////////////////////////////////// 4722SN/A 473395SN/A// Map of class names to SerializableBuilder creation functions. 4742SN/A// Need to make this a pointer so we can force initialization on the 475395SN/A// first reference; otherwise, some SerializableClass constructors 4762SN/A// may be invoked before the classMap constructor. 4776225Snate@binkert.orgmap<string, SerializableClass::CreateFunc> *SerializableClass::classMap = 0; 4782SN/A 479395SN/A// SerializableClass constructor: add mapping to classMap 480395SN/ASerializableClass::SerializableClass(const string &className, 4816225Snate@binkert.org CreateFunc createFunc) 4822SN/A{ 4832SN/A if (classMap == NULL) 4846225Snate@binkert.org classMap = new map<string, SerializableClass::CreateFunc>(); 4852SN/A 4862SN/A if ((*classMap)[className]) 4876225Snate@binkert.org fatal("Error: simulation object class %s redefined\n", className); 4882SN/A 4892SN/A // add className --> createFunc to class map 4902SN/A (*classMap)[className] = createFunc; 4912SN/A} 4922SN/A 4932SN/A// 4942SN/A// 495395SN/ASerializable * 4966225Snate@binkert.orgSerializableClass::createObject(Checkpoint *cp, const string §ion) 4972SN/A{ 498237SN/A string className; 4992SN/A 500237SN/A if (!cp->find(section, "type", className)) { 501395SN/A fatal("Serializable::create: no 'type' entry in section '%s'.\n", 502237SN/A section); 5032SN/A } 5042SN/A 505237SN/A CreateFunc createFunc = (*classMap)[className]; 506237SN/A 507237SN/A if (createFunc == NULL) { 508395SN/A fatal("Serializable::create: no create function for class '%s'.\n", 509237SN/A className); 5102SN/A } 5112SN/A 512395SN/A Serializable *object = createFunc(cp, section); 5132SN/A 5142SN/A assert(object != NULL); 5152SN/A 5162SN/A return object; 5172SN/A} 5182SN/A 519237SN/A 520395SN/ASerializable * 5216225Snate@binkert.orgSerializable::create(Checkpoint *cp, const string §ion) 522237SN/A{ 523395SN/A Serializable *object = SerializableClass::createObject(cp, section); 524237SN/A object->unserialize(cp, section); 525237SN/A return object; 526237SN/A} 527237SN/A 528237SN/A 5297491Ssteve.reinhardt@amd.comconst char *Checkpoint::baseFilename = "m5.cpt"; 5307491Ssteve.reinhardt@amd.com 5317491Ssteve.reinhardt@amd.comstring Checkpoint::currentDirectory; 5327491Ssteve.reinhardt@amd.com 5337491Ssteve.reinhardt@amd.comstring 5347491Ssteve.reinhardt@amd.comCheckpoint::setDir(const string &name) 5357491Ssteve.reinhardt@amd.com{ 5367491Ssteve.reinhardt@amd.com // use csprintf to insert curTick into directory name if it 5377491Ssteve.reinhardt@amd.com // appears to have a format placeholder in it. 5387491Ssteve.reinhardt@amd.com currentDirectory = (name.find("%") != string::npos) ? 5397491Ssteve.reinhardt@amd.com csprintf(name, curTick) : name; 5407491Ssteve.reinhardt@amd.com if (currentDirectory[currentDirectory.size() - 1] != '/') 5417491Ssteve.reinhardt@amd.com currentDirectory += "/"; 5427491Ssteve.reinhardt@amd.com return currentDirectory; 5437491Ssteve.reinhardt@amd.com} 5447491Ssteve.reinhardt@amd.com 5457491Ssteve.reinhardt@amd.comstring 5467491Ssteve.reinhardt@amd.comCheckpoint::dir() 5477491Ssteve.reinhardt@amd.com{ 5487491Ssteve.reinhardt@amd.com return currentDirectory; 5497491Ssteve.reinhardt@amd.com} 5507491Ssteve.reinhardt@amd.com 5517491Ssteve.reinhardt@amd.com 5527491Ssteve.reinhardt@amd.comCheckpoint::Checkpoint(const string &cpt_dir) 5537532Ssteve.reinhardt@amd.com : db(new IniFile), cptDir(setDir(cpt_dir)) 554237SN/A{ 5557532Ssteve.reinhardt@amd.com string filename = cptDir + "/" + Checkpoint::baseFilename; 556237SN/A if (!db->load(filename)) { 557237SN/A fatal("Can't load checkpoint file '%s'\n", filename); 558237SN/A } 559237SN/A} 560237SN/A 561237SN/A 562237SN/Abool 5636225Snate@binkert.orgCheckpoint::find(const string §ion, const string &entry, string &value) 564237SN/A{ 565237SN/A return db->find(section, entry, value); 566237SN/A} 567237SN/A 568237SN/A 569237SN/Abool 5706225Snate@binkert.orgCheckpoint::findObj(const string §ion, const string &entry, 5714000Ssaidi@eecs.umich.edu SimObject *&value) 572237SN/A{ 573237SN/A string path; 574237SN/A 575237SN/A if (!db->find(section, entry, path)) 576237SN/A return false; 577237SN/A 5784000Ssaidi@eecs.umich.edu value = resolveSimObject(path); 5794000Ssaidi@eecs.umich.edu return true; 580237SN/A} 581304SN/A 582304SN/A 583304SN/Abool 5846225Snate@binkert.orgCheckpoint::sectionExists(const string §ion) 585304SN/A{ 586304SN/A return db->sectionExists(section); 587304SN/A} 588