serialize.cc revision 6820
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 904762Snate@binkert.orgshowParam(ostream &os, const char &value) 914762Snate@binkert.org{ 924762Snate@binkert.org os << (int)value; 934762Snate@binkert.org} 944762Snate@binkert.org 954762Snate@binkert.org 964762Snate@binkert.orgtemplate <> 974762Snate@binkert.orgvoid 984762Snate@binkert.orgshowParam(ostream &os, const unsigned char &value) 994762Snate@binkert.org{ 1004762Snate@binkert.org os << (unsigned int)value; 1014762Snate@binkert.org} 1024762Snate@binkert.org 1034762Snate@binkert.org 1044762Snate@binkert.org// Use sscanf() for FP types as to_number() only handles integers 1054762Snate@binkert.orgtemplate <> 1064762Snate@binkert.orgbool 1074762Snate@binkert.orgparseParam(const string &s, float &value) 1084762Snate@binkert.org{ 1094762Snate@binkert.org return (sscanf(s.c_str(), "%f", &value) == 1); 1104762Snate@binkert.org} 1114762Snate@binkert.org 1124762Snate@binkert.orgtemplate <> 1134762Snate@binkert.orgbool 1144762Snate@binkert.orgparseParam(const string &s, double &value) 1154762Snate@binkert.org{ 1164762Snate@binkert.org return (sscanf(s.c_str(), "%lf", &value) == 1); 1174762Snate@binkert.org} 1184762Snate@binkert.org 1194762Snate@binkert.orgtemplate <> 1204762Snate@binkert.orgbool 1214762Snate@binkert.orgparseParam(const string &s, bool &value) 1224762Snate@binkert.org{ 1234762Snate@binkert.org const string &ls = to_lower(s); 1244762Snate@binkert.org 1254762Snate@binkert.org if (ls == "true") { 1264762Snate@binkert.org value = true; 1274762Snate@binkert.org return true; 1284762Snate@binkert.org } 1294762Snate@binkert.org 1304762Snate@binkert.org if (ls == "false") { 1314762Snate@binkert.org value = false; 1324762Snate@binkert.org return true; 1334762Snate@binkert.org } 1344762Snate@binkert.org 1354762Snate@binkert.org return false; 1364762Snate@binkert.org} 1374762Snate@binkert.org 1384762Snate@binkert.org// Display bools as strings 1394762Snate@binkert.orgtemplate <> 1404762Snate@binkert.orgvoid 1414762Snate@binkert.orgshowParam(ostream &os, const bool &value) 1424762Snate@binkert.org{ 1434762Snate@binkert.org os << (value ? "true" : "false"); 1444762Snate@binkert.org} 1454762Snate@binkert.org 1464762Snate@binkert.org 1474762Snate@binkert.org// String requires no processing to speak of 1484762Snate@binkert.orgtemplate <> 1494762Snate@binkert.orgbool 1504762Snate@binkert.orgparseParam(const string &s, string &value) 1514762Snate@binkert.org{ 1524762Snate@binkert.org value = s; 1534762Snate@binkert.org return true; 1544762Snate@binkert.org} 1554762Snate@binkert.org 1562287SN/Aint Serializable::ckptMaxCount = 0; 1572287SN/Aint Serializable::ckptCount = 0; 1582287SN/Aint Serializable::ckptPrevCount = -1; 1591637SN/A 1602SN/Avoid 161395SN/ASerializable::nameOut(ostream &os) 1622SN/A{ 163217SN/A os << "\n[" << name() << "]\n"; 1642SN/A} 1652SN/A 1662SN/Avoid 167395SN/ASerializable::nameOut(ostream &os, const string &_name) 1682SN/A{ 169217SN/A os << "\n[" << _name << "]\n"; 1702SN/A} 1712SN/A 172217SN/Atemplate <class T> 1732SN/Avoid 1746225Snate@binkert.orgparamOut(ostream &os, const string &name, const T ¶m) 1752SN/A{ 176217SN/A os << name << "="; 177217SN/A showParam(os, param); 178217SN/A os << "\n"; 1792SN/A} 1802SN/A 1814841Ssaidi@eecs.umich.edutemplate <class T> 1824841Ssaidi@eecs.umich.eduvoid 1836225Snate@binkert.orgarrayParamOut(ostream &os, const string &name, const vector<T> ¶m) 1844841Ssaidi@eecs.umich.edu{ 1856227Snate@binkert.org typename vector<T>::size_type size = param.size(); 1864841Ssaidi@eecs.umich.edu os << name << "="; 1874841Ssaidi@eecs.umich.edu if (size > 0) 1884841Ssaidi@eecs.umich.edu showParam(os, param[0]); 1896227Snate@binkert.org for (typename vector<T>::size_type i = 1; i < size; ++i) { 1904841Ssaidi@eecs.umich.edu os << " "; 1914841Ssaidi@eecs.umich.edu showParam(os, param[i]); 1924841Ssaidi@eecs.umich.edu } 1934841Ssaidi@eecs.umich.edu os << "\n"; 1944841Ssaidi@eecs.umich.edu} 1954841Ssaidi@eecs.umich.edu 196217SN/A 197217SN/Atemplate <class T> 198217SN/Avoid 1996225Snate@binkert.orgparamIn(Checkpoint *cp, const string §ion, const string &name, T ¶m) 2002SN/A{ 2016225Snate@binkert.org string str; 202237SN/A if (!cp->find(section, name, str) || !parseParam(str, param)) { 203217SN/A fatal("Can't unserialize '%s:%s'\n", section, name); 204217SN/A } 2052SN/A} 2062SN/A 2076820SLisa.Hsu@amd.comtemplate <class T> 2086820SLisa.Hsu@amd.combool 2096820SLisa.Hsu@amd.comoptParamIn(Checkpoint *cp, const string §ion, const string &name, T ¶m) 2106820SLisa.Hsu@amd.com{ 2116820SLisa.Hsu@amd.com string str; 2126820SLisa.Hsu@amd.com if (!cp->find(section, name, str) || !parseParam(str, param)) { 2136820SLisa.Hsu@amd.com warn("optional parameter %s:%s not present\n", section, name); 2146820SLisa.Hsu@amd.com return false; 2156820SLisa.Hsu@amd.com } else { 2166820SLisa.Hsu@amd.com return true; 2176820SLisa.Hsu@amd.com } 2186820SLisa.Hsu@amd.com} 219217SN/A 220217SN/Atemplate <class T> 221217SN/Avoid 2226227Snate@binkert.orgarrayParamOut(ostream &os, const string &name, const T *param, unsigned size) 223217SN/A{ 224217SN/A os << name << "="; 225217SN/A if (size > 0) 226217SN/A showParam(os, param[0]); 2276227Snate@binkert.org for (unsigned i = 1; i < size; ++i) { 228217SN/A os << " "; 229217SN/A showParam(os, param[i]); 230217SN/A } 231217SN/A os << "\n"; 232217SN/A} 233217SN/A 234217SN/A 235217SN/Atemplate <class T> 236217SN/Avoid 2376225Snate@binkert.orgarrayParamIn(Checkpoint *cp, const string §ion, const string &name, 2386227Snate@binkert.org T *param, unsigned size) 239217SN/A{ 2406225Snate@binkert.org string str; 241237SN/A if (!cp->find(section, name, str)) { 242217SN/A fatal("Can't unserialize '%s:%s'\n", section, name); 243217SN/A } 244217SN/A 245217SN/A // code below stolen from VectorParam<T>::parse(). 246217SN/A // it would be nice to unify these somehow... 247217SN/A 248217SN/A vector<string> tokens; 249217SN/A 250217SN/A tokenize(tokens, str, ' '); 251217SN/A 252217SN/A // Need this if we were doing a vector 253217SN/A // value.resize(tokens.size()); 254217SN/A 255217SN/A if (tokens.size() != size) { 256217SN/A fatal("Array size mismatch on %s:%s'\n", section, name); 257217SN/A } 258217SN/A 2596227Snate@binkert.org for (vector<string>::size_type i = 0; i < tokens.size(); i++) { 260217SN/A // need to parse into local variable to handle vector<bool>, 261217SN/A // for which operator[] returns a special reference class 262217SN/A // that's not the same as 'bool&', (since it's a packed 263217SN/A // vector) 264217SN/A T scalar_value; 265217SN/A if (!parseParam(tokens[i], scalar_value)) { 266217SN/A string err("could not parse \""); 267217SN/A 268217SN/A err += str; 269217SN/A err += "\""; 270217SN/A 271217SN/A fatal(err); 272217SN/A } 273217SN/A 274217SN/A // assign parsed value to vector 275217SN/A param[i] = scalar_value; 276217SN/A } 277217SN/A} 278217SN/A 2794841Ssaidi@eecs.umich.edutemplate <class T> 2804841Ssaidi@eecs.umich.eduvoid 2816225Snate@binkert.orgarrayParamIn(Checkpoint *cp, const string §ion, 2826225Snate@binkert.org const string &name, vector<T> ¶m) 2834841Ssaidi@eecs.umich.edu{ 2846225Snate@binkert.org string str; 2854841Ssaidi@eecs.umich.edu if (!cp->find(section, name, str)) { 2864841Ssaidi@eecs.umich.edu fatal("Can't unserialize '%s:%s'\n", section, name); 2874841Ssaidi@eecs.umich.edu } 2884841Ssaidi@eecs.umich.edu 2894841Ssaidi@eecs.umich.edu // code below stolen from VectorParam<T>::parse(). 2904841Ssaidi@eecs.umich.edu // it would be nice to unify these somehow... 2914841Ssaidi@eecs.umich.edu 2924841Ssaidi@eecs.umich.edu vector<string> tokens; 2934841Ssaidi@eecs.umich.edu 2944841Ssaidi@eecs.umich.edu tokenize(tokens, str, ' '); 2954841Ssaidi@eecs.umich.edu 2964841Ssaidi@eecs.umich.edu // Need this if we were doing a vector 2974841Ssaidi@eecs.umich.edu // value.resize(tokens.size()); 2984841Ssaidi@eecs.umich.edu 2994841Ssaidi@eecs.umich.edu param.resize(tokens.size()); 3004841Ssaidi@eecs.umich.edu 3016227Snate@binkert.org for (vector<string>::size_type i = 0; i < tokens.size(); i++) { 3024841Ssaidi@eecs.umich.edu // need to parse into local variable to handle vector<bool>, 3034841Ssaidi@eecs.umich.edu // for which operator[] returns a special reference class 3044841Ssaidi@eecs.umich.edu // that's not the same as 'bool&', (since it's a packed 3054841Ssaidi@eecs.umich.edu // vector) 3064841Ssaidi@eecs.umich.edu T scalar_value; 3074841Ssaidi@eecs.umich.edu if (!parseParam(tokens[i], scalar_value)) { 3084841Ssaidi@eecs.umich.edu string err("could not parse \""); 3094841Ssaidi@eecs.umich.edu 3104841Ssaidi@eecs.umich.edu err += str; 3114841Ssaidi@eecs.umich.edu err += "\""; 3124841Ssaidi@eecs.umich.edu 3134841Ssaidi@eecs.umich.edu fatal(err); 3144841Ssaidi@eecs.umich.edu } 3154841Ssaidi@eecs.umich.edu 3164841Ssaidi@eecs.umich.edu // assign parsed value to vector 3174841Ssaidi@eecs.umich.edu param[i] = scalar_value; 3184841Ssaidi@eecs.umich.edu } 3194841Ssaidi@eecs.umich.edu} 3204841Ssaidi@eecs.umich.edu 321237SN/Avoid 3226225Snate@binkert.orgobjParamIn(Checkpoint *cp, const string §ion, 3236225Snate@binkert.org const string &name, SimObject * ¶m) 324237SN/A{ 325237SN/A if (!cp->findObj(section, name, param)) { 326237SN/A fatal("Can't unserialize '%s:%s'\n", section, name); 327237SN/A } 328237SN/A} 329237SN/A 330237SN/A 3315543Ssaidi@eecs.umich.edu#define INSTANTIATE_PARAM_TEMPLATES(type) \ 3325543Ssaidi@eecs.umich.edutemplate void \ 3336225Snate@binkert.orgparamOut(ostream &os, const string &name, type const ¶m); \ 3345543Ssaidi@eecs.umich.edutemplate void \ 3356225Snate@binkert.orgparamIn(Checkpoint *cp, const string §ion, \ 3366225Snate@binkert.org const string &name, type & param); \ 3376820SLisa.Hsu@amd.comtemplate bool \ 3386820SLisa.Hsu@amd.comoptParamIn(Checkpoint *cp, const string §ion, \ 3396820SLisa.Hsu@amd.com const string &name, type & param); \ 3405543Ssaidi@eecs.umich.edutemplate void \ 3416225Snate@binkert.orgarrayParamOut(ostream &os, const string &name, \ 3426227Snate@binkert.org type const *param, unsigned size); \ 3435543Ssaidi@eecs.umich.edutemplate void \ 3446225Snate@binkert.orgarrayParamIn(Checkpoint *cp, const string §ion, \ 3456227Snate@binkert.org const string &name, type *param, unsigned size); \ 3465543Ssaidi@eecs.umich.edutemplate void \ 3476225Snate@binkert.orgarrayParamOut(ostream &os, const string &name, \ 3486225Snate@binkert.org const vector<type> ¶m); \ 3495543Ssaidi@eecs.umich.edutemplate void \ 3506225Snate@binkert.orgarrayParamIn(Checkpoint *cp, const string §ion, \ 3516225Snate@binkert.org const string &name, vector<type> ¶m); 352217SN/A 3531642SN/AINSTANTIATE_PARAM_TEMPLATES(signed char) 3541642SN/AINSTANTIATE_PARAM_TEMPLATES(unsigned char) 3551642SN/AINSTANTIATE_PARAM_TEMPLATES(signed short) 3561642SN/AINSTANTIATE_PARAM_TEMPLATES(unsigned short) 3571642SN/AINSTANTIATE_PARAM_TEMPLATES(signed int) 3581642SN/AINSTANTIATE_PARAM_TEMPLATES(unsigned int) 3591642SN/AINSTANTIATE_PARAM_TEMPLATES(signed long) 3601642SN/AINSTANTIATE_PARAM_TEMPLATES(unsigned long) 3611642SN/AINSTANTIATE_PARAM_TEMPLATES(signed long long) 3621642SN/AINSTANTIATE_PARAM_TEMPLATES(unsigned long long) 363219SN/AINSTANTIATE_PARAM_TEMPLATES(bool) 3645992Snate@binkert.orgINSTANTIATE_PARAM_TEMPLATES(float) 3655992Snate@binkert.orgINSTANTIATE_PARAM_TEMPLATES(double) 366217SN/AINSTANTIATE_PARAM_TEMPLATES(string) 367217SN/A 368217SN/A 369395SN/A///////////////////////////// 370395SN/A 371395SN/A/// Container for serializing global variables (not associated with 372395SN/A/// any serialized object). 373395SN/Aclass Globals : public Serializable 3742SN/A{ 375395SN/A public: 376512SN/A const string name() const; 377510SN/A void serialize(ostream &os); 378395SN/A void unserialize(Checkpoint *cp); 379395SN/A}; 3802SN/A 381395SN/A/// The one and only instance of the Globals class. 382395SN/AGlobals globals; 3832SN/A 384512SN/Aconst string 385395SN/AGlobals::name() const 3862SN/A{ 387395SN/A return "Globals"; 3882SN/A} 3892SN/A 3902SN/Avoid 391510SN/AGlobals::serialize(ostream &os) 3922SN/A{ 393395SN/A nameOut(os); 394395SN/A SERIALIZE_SCALAR(curTick); 395395SN/A 396395SN/A nameOut(os, "MainEventQueue"); 397395SN/A mainEventQueue.serialize(os); 3982SN/A} 3992SN/A 4002SN/Avoid 401395SN/AGlobals::unserialize(Checkpoint *cp) 4022SN/A{ 403395SN/A const string §ion = name(); 404395SN/A UNSERIALIZE_SCALAR(curTick); 4052SN/A 406395SN/A mainEventQueue.unserialize(cp, "MainEventQueue"); 4072SN/A} 4082SN/A 4095739Snate@binkert.orgSerializable::Serializable() 4105739Snate@binkert.org{ 4115739Snate@binkert.org} 4125739Snate@binkert.org 4135739Snate@binkert.orgSerializable::~Serializable() 4145739Snate@binkert.org{ 4155739Snate@binkert.org} 4165739Snate@binkert.org 4175739Snate@binkert.orgvoid 4186225Snate@binkert.orgSerializable::serialize(ostream &os) 4195739Snate@binkert.org{ 4205739Snate@binkert.org} 4215739Snate@binkert.org 4225739Snate@binkert.orgvoid 4236225Snate@binkert.orgSerializable::unserialize(Checkpoint *cp, const string §ion) 4245739Snate@binkert.org{ 4255739Snate@binkert.org} 4265739Snate@binkert.org 4272SN/Avoid 4286225Snate@binkert.orgSerializable::serializeAll(const string &cpt_dir) 4292SN/A{ 4302868Sktlim@umich.edu setCheckpointDir(cpt_dir); 431449SN/A string dir = Checkpoint::dir(); 432363SN/A if (mkdir(dir.c_str(), 0775) == -1 && errno != EEXIST) 433449SN/A fatal("couldn't mkdir %s\n", dir); 434363SN/A 435449SN/A string cpt_file = dir + Checkpoint::baseFilename; 436395SN/A ofstream outstream(cpt_file.c_str()); 4372SN/A time_t t = time(NULL); 4385581Ssaidi@eecs.umich.edu if (!outstream.is_open()) 4395581Ssaidi@eecs.umich.edu fatal("Unable to open file %s for writing\n", cpt_file.c_str()); 4406818SLisa.Hsu@amd.com outstream << "## checkpoint generated: " << ctime(&t); 4412SN/A 442395SN/A globals.serialize(outstream); 443395SN/A SimObject::serializeAll(outstream); 444395SN/A} 4452SN/A 4462797Sktlim@umich.eduvoid 4476225Snate@binkert.orgSerializable::unserializeAll(const string &cpt_dir) 4482797Sktlim@umich.edu{ 4492868Sktlim@umich.edu setCheckpointDir(cpt_dir); 4502797Sktlim@umich.edu string dir = Checkpoint::dir(); 4512797Sktlim@umich.edu string cpt_file = dir + Checkpoint::baseFilename; 4522797Sktlim@umich.edu string section = ""; 4532797Sktlim@umich.edu 4542797Sktlim@umich.edu DPRINTFR(Config, "Loading checkpoint dir '%s'\n", 4552797Sktlim@umich.edu dir); 4562797Sktlim@umich.edu Checkpoint *cp = new Checkpoint(dir, section); 4572797Sktlim@umich.edu unserializeGlobals(cp); 4582797Sktlim@umich.edu SimObject::unserializeAll(cp); 4592797Sktlim@umich.edu} 4602SN/A 461395SN/Avoid 462395SN/ASerializable::unserializeGlobals(Checkpoint *cp) 463395SN/A{ 464395SN/A globals.unserialize(cp); 465395SN/A} 4662SN/A 467449SN/Aconst char *Checkpoint::baseFilename = "m5.cpt"; 468449SN/A 469449SN/Astatic string checkpointDirBase; 470294SN/A 4712797Sktlim@umich.eduvoid 4726225Snate@binkert.orgsetCheckpointDir(const string &name) 4732797Sktlim@umich.edu{ 4742797Sktlim@umich.edu checkpointDirBase = name; 4752797Sktlim@umich.edu if (checkpointDirBase[checkpointDirBase.size() - 1] != '/') 4762797Sktlim@umich.edu checkpointDirBase += "/"; 4772797Sktlim@umich.edu} 4782797Sktlim@umich.edu 479294SN/Astring 480449SN/ACheckpoint::dir() 481294SN/A{ 482449SN/A // use csprintf to insert curTick into directory name if it 483449SN/A // appears to have a format placeholder in it. 484449SN/A return (checkpointDirBase.find("%") != string::npos) ? 485449SN/A csprintf(checkpointDirBase, curTick) : checkpointDirBase; 4862SN/A} 4872SN/A 4882SN/Avoid 4896225Snate@binkert.orgdebug_serialize(const string &cpt_dir) 4902SN/A{ 4912868Sktlim@umich.edu Serializable::serializeAll(cpt_dir); 4922SN/A} 4932SN/A 4942SN/A 4952SN/A//////////////////////////////////////////////////////////////////////// 4962SN/A// 497395SN/A// SerializableClass member definitions 4982SN/A// 4992SN/A//////////////////////////////////////////////////////////////////////// 5002SN/A 501395SN/A// Map of class names to SerializableBuilder creation functions. 5022SN/A// Need to make this a pointer so we can force initialization on the 503395SN/A// first reference; otherwise, some SerializableClass constructors 5042SN/A// may be invoked before the classMap constructor. 5056225Snate@binkert.orgmap<string, SerializableClass::CreateFunc> *SerializableClass::classMap = 0; 5062SN/A 507395SN/A// SerializableClass constructor: add mapping to classMap 508395SN/ASerializableClass::SerializableClass(const string &className, 5096225Snate@binkert.org CreateFunc createFunc) 5102SN/A{ 5112SN/A if (classMap == NULL) 5126225Snate@binkert.org classMap = new map<string, SerializableClass::CreateFunc>(); 5132SN/A 5142SN/A if ((*classMap)[className]) 5156225Snate@binkert.org fatal("Error: simulation object class %s redefined\n", className); 5162SN/A 5172SN/A // add className --> createFunc to class map 5182SN/A (*classMap)[className] = createFunc; 5192SN/A} 5202SN/A 5212SN/A// 5222SN/A// 523395SN/ASerializable * 5246225Snate@binkert.orgSerializableClass::createObject(Checkpoint *cp, const string §ion) 5252SN/A{ 526237SN/A string className; 5272SN/A 528237SN/A if (!cp->find(section, "type", className)) { 529395SN/A fatal("Serializable::create: no 'type' entry in section '%s'.\n", 530237SN/A section); 5312SN/A } 5322SN/A 533237SN/A CreateFunc createFunc = (*classMap)[className]; 534237SN/A 535237SN/A if (createFunc == NULL) { 536395SN/A fatal("Serializable::create: no create function for class '%s'.\n", 537237SN/A className); 5382SN/A } 5392SN/A 540395SN/A Serializable *object = createFunc(cp, section); 5412SN/A 5422SN/A assert(object != NULL); 5432SN/A 5442SN/A return object; 5452SN/A} 5462SN/A 547237SN/A 548395SN/ASerializable * 5496225Snate@binkert.orgSerializable::create(Checkpoint *cp, const string §ion) 550237SN/A{ 551395SN/A Serializable *object = SerializableClass::createObject(cp, section); 552237SN/A object->unserialize(cp, section); 553237SN/A return object; 554237SN/A} 555237SN/A 556237SN/A 5576225Snate@binkert.orgCheckpoint::Checkpoint(const string &cpt_dir, const string &path) 5582738Sstever@eecs.umich.edu : db(new IniFile), basePath(path), cptDir(cpt_dir) 559237SN/A{ 560449SN/A string filename = cpt_dir + "/" + Checkpoint::baseFilename; 561237SN/A if (!db->load(filename)) { 562237SN/A fatal("Can't load checkpoint file '%s'\n", filename); 563237SN/A } 564237SN/A} 565237SN/A 566237SN/A 567237SN/Abool 5686225Snate@binkert.orgCheckpoint::find(const string §ion, const string &entry, string &value) 569237SN/A{ 570237SN/A return db->find(section, entry, value); 571237SN/A} 572237SN/A 573237SN/A 574237SN/Abool 5756225Snate@binkert.orgCheckpoint::findObj(const string §ion, const string &entry, 5764000Ssaidi@eecs.umich.edu SimObject *&value) 577237SN/A{ 578237SN/A string path; 579237SN/A 580237SN/A if (!db->find(section, entry, path)) 581237SN/A return false; 582237SN/A 5834000Ssaidi@eecs.umich.edu value = resolveSimObject(path); 5844000Ssaidi@eecs.umich.edu return true; 585237SN/A} 586304SN/A 587304SN/A 588304SN/Abool 5896225Snate@binkert.orgCheckpoint::sectionExists(const string §ion) 590304SN/A{ 591304SN/A return db->sectionExists(section); 592304SN/A} 593