Пример #1
0
EXPORT_C TInt CTestConfig::ItemValue(const TDesC8& aSection, const TDesC8& aItem, const TInt aDefault) const
	{
	TInt output = aDefault;
	const CTestConfigSection* section = Section(aSection);

	if (section != NULL)
		{
		output = section->ItemValue(aItem, aDefault);
		}

	return output;
	}
Пример #2
0
long
DCirfile::GetItemCount(void)
{
	long count = 0;

	while (NextItem())
		count++;

	Section(CurrSectName);

	return count;
}
Пример #3
0
Section& File::section(const std::string &name)
{
    auto it = _sectionIdxMap.find(name);
    if (it == _sectionIdxMap.end())
    {
        auto idx = _sections.size();
        _sections.push_back(std::move(Section(name)));
        _sectionIdxMap[name] = idx;
        return _sections.at(idx);
    }
    return _sections.at(it->second);
}
Пример #4
0
EXPORT_C TInt CScriptFile::ItemValue(const TDesC& aSection, const TDesC& aItem, const TInt aDefault)
	{
	TInt output = aDefault;
	CScriptSection* section = Section(aSection);

	if (section != NULL)
		{
		output = section->ItemValue(aItem, aDefault);
		}

	return output;
	}
Пример #5
0
bool IniFile::Load(std::istream &in) {
	// Maximum number of letters in a line
	static const int MAX_BYTES = 1024*32;

	while (!in.eof())
	{
		char templine[MAX_BYTES];
		in.getline(templine, MAX_BYTES);
		std::string line = templine;

		// Remove UTF-8 byte order marks.
		if (line.substr(0, 3) == "\xEF\xBB\xBF")
			line = line.substr(3);
		 
#ifndef _WIN32
		// Check for CRLF eol and convert it to LF
		if (!line.empty() && line.at(line.size()-1) == '\r')
		{
			line.erase(line.size()-1);
		}
#endif

		if (in.eof()) break;

		if (line.size() > 0)
		{
			if (line[0] == '[')
			{
				size_t endpos = line.find("]");

				if (endpos != std::string::npos)
				{
					// New section!
					std::string sub = line.substr(1, endpos - 1);
					sections.push_back(Section(sub));

					if (endpos + 1 < line.size())
					{
						sections[sections.size() - 1].comment = line.substr(endpos + 1);
					}
				}
			}
			else
			{
				if (sections.size() > 0)
					sections[sections.size() - 1].lines.push_back(line);
			}
		}
	}

	return true;
}
Пример #6
0
void CCLientName::Delete(CString strName)
{
	CDataCriticalSection Section(&m_oCriticalSection);

	for (UINT i = 0; i < m_arrName.GetCount(); i++)
	{
		if (m_arrName[i].ModuleName == strName)
		{
			m_arrName.RemoveAt(i);
			break;
		}
	}
}
Пример #7
0
void IniFile::writeString(const String& strSection, const String& strKey, const String& strVal)
{
    m_isChanged=true;
    Section* section=findSection(strSection);
    if (section == 0)
    {
        m_sctList.push_back(Section(strSection));
        m_sctList.back().writeString(strKey, strVal);
    }
    else
    {
        section->writeString(strKey, strVal);
    }
}
Пример #8
0
void CTraceFileLog::Write(LPCTSTR Message, bool EndOfLine )
{
	if (!m_hLogFile.IsOpen()) { return; }
	
	CGuard Section(m_CriticalSection);
	m_hLogFile.Log(Message);
	if (EndOfLine)
	{
		m_hLogFile.Log(_T("\r\n"));
		if (m_FlushFile)
		{
			m_hLogFile.Flush();
		}
	}
}
Пример #9
0
bool IniFile::Load(const char* filename)
{
	sections.clear();
	sections.push_back(Section(""));
	// first section consists of the comments before the first real section

	// Open file
	std::ifstream in;
	in.open(filename, std::ios::in);

	if (in.fail()) return false;

	bool success = Load(in);
	in.close();
	return success;
}
Пример #10
0
void IniFile::parseText(BufInputStream& txtFile)
{
    //txtFile.seek(0, skBegin);
    clearList();
    const char notesFlag = ';';
    String strLine;
    while (txtFile.readLine(strLine))
    {
        trimTo(strLine);
        String& strTmp=strLine;
        long strTmp_size=(long)strTmp.size();
        //Notes
        if ((strTmp_size > 0) && (notesFlag != strTmp[0]))		
        {
            //Section
            if (strTmp_size >= 2)
            {
                if ((sectionStart == strTmp[0]) && (sectionEnd == strTmp[strTmp_size - 1]))
                {
                    String strSection;
                    trim(strTmp.c_str()+1,strTmp_size-2,strSection);
                    m_sctList.push_back(Section(strSection));
                }
                else
                {
                    long nIdxSpace = findStr(strTmp, valSpace);
                    if (nIdxSpace >= 0) {
                        String strKey;
                        trim(strTmp.c_str(),nIdxSpace,strKey);
                        
                        String strVal;
                        if ((nIdxSpace + 1) < strTmp_size) 
                            trim(strTmp.c_str()+nIdxSpace + 1,strTmp_size - nIdxSpace - 1,strVal);
                        getBackSection()->list.push_back(IniValue(strKey, strVal));
                    }
                    //else getBackSection()->list.push_back(IniValue(strLine));					
                }				
            }
            //else getBackSection()->list.push_back(IniValue(strLine));
        }
        else 
        {
            getBackSection()->list.push_back(IniValue(strLine));
        }
    }	
}
Пример #11
0
static int
Parse (FILE * fp, int (*sfunc) (char *), int (*pfunc) (char * option, char * value, int num_flags, char** flags))
{
    int c;
    c = eatWhitespace (fp);

    while ((c != EOF) && (c > 0))
    {

        switch (c)
        {
            case '\n':      /* blank line */
                {
                    c = eatWhitespace (fp);
                    break;
                }

            case ';':       /* comment line */
            case '#':
                {
                    c = eatComment (fp);
                    break;
                }

            case '[':       /* section header */
                {
                    if (Section (fp, sfunc) < 0)
                    {
                        return (-1);
                    }
                    c = eatWhitespace (fp);
                    break;
                }
            default:        /* parameter line */
                {
                    if (Parameter (fp, pfunc, c) < 0)
                        return (-1);
                    c = eatWhitespace (fp);
                }
        }
    }

    return 0;
}
Пример #12
0
bool IniFile::Load(const char* filename)
{
	sections.clear();
	sections.push_back(Section(""));
	// first section consists of the comments before the first real section

	// Open file
	std::ifstream in;
#ifdef _WIN32
	in.open(ConvertUTF8ToWString(filename), std::ios::in);
#else
	in.open(filename, std::ios::in);
#endif
	if (in.fail()) return false;

	bool success = Load(in);
	in.close();
	return success;
}
Пример #13
0
bool PSIPTable::VerifyPSIP(bool verify_crc) const
{
    if (verify_crc && (CalcCRC() != CRC()))
    {
        LOG(VB_SIPARSER, LOG_ERR,
            QString("PSIPTable: Failed CRC check 0x%1 != 0x%2 "
                    "for StreamID = 0x%3")
                .arg(CRC(),0,16).arg(CalcCRC(),0,16).arg(StreamID(),0,16));
        return false;
    }

    unsigned char *bufend = _fullbuffer + _allocSize;

    if ((_pesdata + 2) >= bufend)
        return false; // can't query length

    if (psipdata() >= bufend)
        return false; // data outside buffer

    if (TableID::PAT == TableID())
    {
        uint pcnt = (SectionLength() - PSIP_OFFSET - 2) >> 2;
        bool ok = (psipdata() + (pcnt << 2) + 3 < bufend);
        if (!ok)
        {
            LOG(VB_SIPARSER, LOG_ERR,
                "PSIPTable: PAT: program list extends past end of buffer");
            return false;
        }

        if ((Length() == 0xfff) && (TableIDExtension() == 0xffff) &&
            (Section() == 0xff) && (LastSection() == 0xff))
        {
            LOG(VB_SIPARSER, LOG_ERR, "PSIPTable: PAT: All values at maximums");
            return false;
        }

        return true;
    }
Пример #14
0
bool ConfigParser::parse(const char *filename)
{
    std::ifstream file(filename);
    std::string line;

    Section section(Section::GLOBAL_SECTION);
    while(std::getline(file,line)){
        //remove whitespaces
        line.erase(remove_if(line.begin(), line.end(), isspace), line.end());

        //skip empty lines
        if (line.compare("") == 0){
            continue;
        }
        //check for section
        if (line.at(0) == '[' && line.at(line.size()-1)){
            //first, add last section to storage
            _config[section.name()] = section;
            //std::cout << section.name() << std::endl;
            // now create new section
            line = line.substr(1, line.size()-2);
            section = Section(line);
        }else{
            size_t eq_pos = line.find_first_of("=");
            if (eq_pos == std::string::npos){
                continue;
            }
            std::string key = line.substr(0,eq_pos);
            std::string val =  line.substr(eq_pos+1, line.size()-1);
            //std::cout << key << " , " << val << std::endl;
            section.add(key, val);

        }

    }

    return true;
}
Пример #15
0
static bool Parse( DATA_BLOB *buf, myFILE *InFile,
                   bool (*sfunc)(const char *, void *),
                   bool (*pfunc)(const char *, const char *, void *),
		   void *userdata)
{
	int    c;

	c = EatWhitespace( InFile );
	while( (EOF != c) && (c > 0) ) {
		switch( c ) {
			case '\n': /* Blank line. */
				c = EatWhitespace( InFile );
				break;

			case ';': /* Comment line. */
			case '#':
				c = EatComment( InFile );
				break;

			case '[': /* Section Header. */
				if( !Section( buf, InFile, sfunc, userdata ) )
					return False;
				c = EatWhitespace( InFile );
				break;

			case '\\': /* Bogus backslash. */
				c = EatWhitespace( InFile );
				break;

			default: /* Parameter line. */
				if( !Parameter( buf, InFile, pfunc, c, userdata ) )
					return False;
				c = EatWhitespace( InFile );
				break;
		}
	}
	return True;
}
Пример #16
0
Section & Section::add_section(const Object & key, bool merge)
{
    if(std::find(this->_lst.begin(), this->_lst.end(), key) != this->_lst.end())
    {
        if(! merge)
        {
            throw SectionError(DEBUG_INFO, "Section " + configment::repr(key) + " already defined");
        }
        Object & p = this->at(key);
        if(! p.get_object().is<Section>())
        {
            throw SectionError(DEBUG_INFO, "Section " + configment::repr(key) + " already defined as key");
        }
        Section * p_section = dynamic_cast<Section *>(&p.get_object());
        return *p_section;
    }
    else
    {
        this->operator [](key) = Section();
        Section * p_section = dynamic_cast<Section *>(&this->operator [](key).get_object());
        return *p_section;
    }
}
Пример #17
0
TEST(Recording_test, constructors)
{
    Recording rec0;
    EXPECT_EQ( rec0.size(), 0 );

    std::vector<Section> sec_list(16, Section(32768));
    Channel ch(sec_list);

    Recording rec1(ch);
    EXPECT_EQ( rec1.size(), 1 );
    EXPECT_EQ( rec1[0].size(), 16 );
    EXPECT_EQ( rec1[0][0].size(), 32768 );

    std::vector<Channel> ch_list(4, Channel(16, 32768));
    Recording rec2(ch_list);
    EXPECT_EQ( rec2.size(), 4 );
    EXPECT_EQ( rec2[rec2.size()-1].size(), 16 );
    EXPECT_EQ( rec2[rec2.size()-1][rec2[rec2.size()-1].size()-1].size(), 32768 );

    Recording rec3(4, 16, 32768);
    EXPECT_EQ( rec3.size(), 4 );
    EXPECT_EQ( rec3[rec3.size()-1].size(), 16 );
    EXPECT_EQ( rec3[rec3.size()-1][rec3[rec3.size()-1].size()-1].size(), 32768 );
}
Пример #18
0
void
DCirfile::GetElemSets(void)
{
	if (!Section("ElementSets"))
		return;

	char *nm = NULL;
	long len = 0;
	while (NextItem()) {  // this gets higher-priority items first
		if ((nm = StrLeft()) == NULL)
			break;
		if (*nm == '$')
			nm++;
		len = strlen(nm);
		while (nm[len - 1] == ' ')
			nm[--len] = '\0';
		if (!*nm)
			continue;
		if (!ElemSetNames(nm)) {  // don't replace higher-priority ones
			ElemSetNames.add(nm, ++ElemSetNum);
			ElemSets.add(StrArrRight(), ElemSetNum);
		}
	}
}
Пример #19
0
DCirfile *
DCirfile::SetConfigTemplate(const char *sect, const char *setting,
		                        bool link)
{
	DCirfile *bottomIni = SecFile ? SecFile : this;
	bool secfound = false;
	char *startdir =  _getcwd(NewName(1024), 1024);
	char *currdir = startdir;
	char *newdir = NULL;
	int startdrive = _getdrive();
	int currdrive = startdrive;
	int newdrive = 0;

	IniLevel = 0;

	if (!LogEventFunc)
		LastConfigSetting = NewName(setting);

	if (SecFile != NULL) {
		IniFileList.add(SecFile, ++IniLevel);
		IniNameList.add(SecFile->getBaseName(), IniLevel);
		IniChainList.add(SecFile->getFilePath(), IniLevel);
	}
	IniFileList.add(this, ++IniLevel);
	IniNameList.add(getBaseName(), IniLevel);
	IniChainList.add(getFilePath(), IniLevel);

	DCirfile *configTpl = NULL;
	char *configTplName = NULL;

	// SecFile (specific ini) overrides tpl choice in this
	DCirfile *topIni = this;
	secfound = Section(sect);

	if (secfound
	 && Find("Scope"))
		Scope = StrRight();

	if (secfound
	 && !stricmp(setting, "configs")
	 && Find("Document")) {   // insert document chain here
		DCirfile *topdoc = this;
		while (topdoc->Section(sect)) {
			if (!topdoc->Find("Document"))
				break;  // end of chain with no end flag ****
			char *nm = topdoc->StrRight();
			if (!nm)
				break;  // end of chain with no end flag ****
			if (!stricmp(nm, "end")) {
				DeleteName(nm);
				topdoc->ChainEnded = true;
				break;  // end of chain with end flag
			}
			DeleteName(nm);
			if ((configTplName = topdoc->PathRight()) == NULL)
				break;  // end of chain with no end flag ****
			if ((configTpl = new DCirfile(configTplName)) == NULL) {
				LogEvent(logwarn, 1, topdoc->getFilePath(), " refers to unopenable ",
					"Document template", " ", NewName(configTplName));
				DeleteName(configTplName);
				configTplName = NULL;
				break;
			}
			if (configTpl->FErr() != fok) {
				LogEvent(logwarn, 1, topdoc->getFilePath(), " refers to nonexistent ",
					"Document template", " ", NewName(configTpl->getFilePath()));
				DeleteName(configTplName);
				configTplName = NULL;
				delete configTpl;
				break;  // file not found
			}
			newdir = configTpl->getBasePath();
			if (*(newdir + 1) == ':')
				newdrive = (toupper(*newdir) - 'A') + 1;
			if (newdrive
			 && (currdrive != newdrive))
				_chdrive(currdrive = newdrive);
			if (stricmp(newdir, currdir))
				_chdir(currdir = newdir);

			if (IniNameList(configTpl->getBaseName())) {
				LogEvent(logwarn, 1, topdoc->getFilePath(), " repeats ",
					"Document template", " ", NewName(configTpl->getFilePath()));
				DeleteName(configTplName);
				configTplName = NULL;
				delete configTpl;
				break;  // deja vu, end of the line
			}

			topdoc = configTpl;  // step up
			if (topdoc->Section("Templates")
			 && topdoc->Find("Scope"))
				topdoc->Scope = topdoc->StrRight();
			DeleteName(configTplName);
			configTplName = NULL;
			IniFileList.add(topdoc, ++IniLevel);
			IniNameList.add(topdoc->getBaseName(), IniLevel);
			IniChainList.add(topdoc->getFilePath(), IniLevel);
		}
	}

	if (!secfound
	 || !Find(setting)) {  // check for old setting
		if (!stricmp(setting, "configs")) {
			if (Section("Setup")
			 && Find("ConfigTemplate")) {
				sect = "Setup";
				setting = "ConfigTemplate";
			}
			else if (Section("FDK")
			 && Find("ConfigTemplate")) {
				sect = "FDK";
				setting = "ConfigTemplate";
			}
		}
		else if (!stricmp(setting, "languages")) {
			if (Section("Setup")
			 && Find("LanguageText"))
				sect = "Setup";
				setting = "LanguageText";
		}
		else if (!stricmp(setting, "macros")) {
			if (Section("Macros")
			 && Find("MacroFile")) {
				sect = "Macros";
				setting = "MacroFile";
			}
		}
	}

	while (topIni->Section(sect)) {
		if (!topIni->Find(setting))
			break;  // end of chain with no end flag ****
		char *nm = topIni->StrRight();
		if (!nm)
			break;  // end of chain with no end flag ****
		if (!stricmp(nm, "end")) {
			DeleteName(nm);
			topIni->ChainEnded = true;
			break;  // end of chain with end flag
		}
		DeleteName(nm);
		if ((configTplName = topIni->PathRight()) == NULL)
			break;  // end of chain with no end flag ****
		if ((configTpl = new DCirfile(configTplName)) == NULL) {
			LogEvent(logwarn, 1, topIni->getFilePath(), " refers to unopenable ",
				setting, " ", NewName(configTplName));
			DeleteName(configTplName);
			configTplName = NULL;
			break;  // can't open file
		}
		if (configTpl->FErr() != fok) {
			LogEvent(logwarn, 1, topIni->getFilePath(), " refers to nonexistent ",
				setting, " ", NewName(configTpl->getFilePath()));
			DeleteName(configTplName);
			configTplName = NULL;
			delete configTpl;
			break;  // file not found
		}
		newdir = configTpl->getBasePath();
		if (*(newdir + 1) == ':')
			newdrive = (toupper(*newdir) - 'A') + 1;
		if (newdrive
		 && (currdrive != newdrive))
			_chdrive(currdrive = newdrive);
		if (stricmp(newdir, currdir))
			_chdir(currdir = newdir);

		if (IniNameList(configTpl->getBaseName())) {
			LogEvent(logwarn, 1, topIni->getFilePath(), " repeats ",
				setting, " ", NewName(configTpl->getFilePath()));
			DeleteName(configTplName);
			configTplName = NULL;
			delete configTpl;
			break;  // deja vu, end of the line
		}

		topIni = configTpl;  // step up
		if (topIni->Section("Templates")
		 && topIni->Find("Scope"))
			topIni->Scope = topIni->StrRight();
		DeleteName(configTplName);
		configTplName = NULL;
		IniFileList.add(topIni, ++IniLevel);
		IniNameList.add(topIni->getBaseName(), IniLevel);
		IniChainList.add(topIni->getFilePath(), IniLevel);
	}

	// topIni is now at the top of the chain, and
	// bottomIni is at the bottom, which may be same.
	if (link) {
		DCirfile *ifl = bottomIni;
		DCirfile *ift = NULL;
		for (long ilev = 1; ilev < IniLevel; ilev++) {
			ift = (DCirfile *) IniFileList.find(ilev + 1);
			if (!ift)
				break;
			ift->SetSecFile(ifl);
			ifl = ift;
			//if (ifl == topIni)
			//	break;
		}
	}

	WriteIniChain(setting);

	if (currdrive != startdrive)
		_chdrive(startdrive);
	if (stricmp(startdir, currdir))
		_chdir(startdir);

	if (this != topIni) {
		topIni->IniFileList = IniFileList;
		topIni->IniNameList = IniNameList;
		topIni->IniChainList = IniChainList;
		topIni->IniLevel = IniLevel;
	}

	return topIni;
}
Пример #20
0
Section Memento::DefaultSection(not_null<PeerData*> peer) {
	if (peer->isSelf()) {
		return Section(Section::MediaType::Photo);
	}
	return Section(Section::Type::Profile);
}
Пример #21
0
PointerWrapSection PointerWrap::Section(const char *title, int ver) {
    return Section(title, ver, ver);
}
Пример #22
0
#include "configParser.h"

static const std::string empty_str = "";
static const Section empty_Sec = Section();

const std::string & 
Section :: get(const std::string key) const
{
    std::map<std::string, std::string>::const_iterator it;
    it = items.find(key);
    if (it != items.end())
        return it->second;
    return empty_str;
} 


bool 
ConfigParser :: parser_file(const std::string &file)
{
    mSections.erase(mSections.begin(), mSections.end());

    std::ifstream instm(file.c_str());
    if (!instm)
        return false;
    std::string line;
    Section *curSection(NULL);
    
    while(instm.peek() != EOF)
    {
        std::getline(instm, line);
        //del last '\r' char
Пример #23
0
Section* IniFile::getBackSection()
{
    if (m_sctList.size() == 0) m_sctList.push_back(Section(""));
    return &m_sctList.back();
}
Пример #24
0
void ObjectFileParser::load_sections() {
#ifdef OFPreadprint
    cout << "Opening " << filename << endl;
#endif
    auto archive_match = filename.find(".a(");
    if (archive_match != string::npos) {
        //archive: /path/to/archive.a(filename.o)
        string archive_filename = filename.substr(0, archive_match+2);
        string file_filename    = filename.substr(archive_match+3, filename.length() -(archive_match+3) -1);

        char templ[] = "/tmp/archived_file_XXXXXX.o";
        auto tmpfd = mkstemps(templ, 2);
        close(tmpfd);
        string tmpfile = string(templ);
        tmpfiles.push_back(tmpfile);
        {
            pid_t pid;
            posix_spawn_file_actions_t act;
            posix_spawn_file_actions_init(&act);
            posix_spawn_file_actions_addopen(&act, 1 /*stdout*/, templ, O_RDWR | O_CREAT, S_IRUSR | S_IWUSR);
            const char* const args[] = {"ar", "p", archive_filename.c_str(), file_filename.c_str(), NULL};
            // posix_spawnp(&pid, "echo", NULL, NULL, (char* const*)args, environ);
            if (0 != posix_spawnp(&pid, "ar", &act, NULL, (char* const*)args, environ))  {
                perror("Can't start ar");
                cerr << "Can't extract file " << filename << " tmpfile: " << tmpfile << endl;
                exit(15);
            }
            int status;
            if (-1 == waitpid(pid, &status, 0)) {
                perror("waitpid failed");
                exit(16);
            }
            if (WEXITSTATUS(status) != 0) {
                cerr << "ar failed. Can't extract file " << filename << " tmpfile: " << tmpfile
                << " exc: " << WEXITSTATUS(status) << endl;
                exit(17);
            }
        }

        if (!reader->load(tmpfile)) {
            cerr << "Can't find or process ELF file " << filename << " tmpfile: " << tmpfile << endl;
            exit(12);
        }
    } else if (filename.find("linker") != string::npos) {
        // linker stubs
        // ignore for now?
    } else {
        // Regular file
        if (!reader->load(filename)) {
            cerr << "Can't find or process ELF file " << filename << endl;
            exit(11);
        }
    }

    // Sections
    for (auto &psec : reader->sections) {
        if (psec->get_name().substr(0, 3) == ".sr") continue;
        _sections.emplace(psec->get_index(), Section(psec->get_name(), psec->get_address(), psec->get_size(),
                                                     /*exec?*/ 0 != (psec->get_flags() & SHF_EXECINSTR),
                                                     /*alloc?*/ 0 != (psec->get_flags() & SHF_ALLOC)));
        _section_id_by_name.emplace(psec->get_name(), psec->get_index());
    }
}
Пример #25
0
	void INI::AddSection(std::string name)
	{
		sections.push_back(Section(name));
	}
Пример #26
0
void DiscreteSlider::addSection(const QString &label) {
	_sections.push_back(Section(label, getLabelFont()));
	resizeToWidth(width());
}
Пример #27
0
Section Memento::section() const {
	return Section(Section::Type::Profile);
}
Пример #28
0
Section Memento::section() const {
	return Section(Section::Type::Channels);
}
Пример #29
0
  bool BytecodeVerification::verify_from(STATE, int sp, int ip,
                                         std::list<Section>& ips)
  {
    if(sp < 0) {
      fail("internal error", ip);
      return false;
    }

    for(;;) {
      int old_sp = stack_[ip];
      if(old_sp < 0) {
        stack_[ip] = sp;
      } else if(old_sp != sp) {
        fail("inconsistent stack depth", ip);
        return false;
      } else {
        // Already been here and stack is consistent, done.
        return true;
      }

      Fixnum* obj = try_as<Fixnum>(ops_->at(ip++));
      if(!obj) {
        fail("corrupt instruction sequence", ip);
        return false;
      }

      opcode op = obj->to_native();
      size_t width = InstructionSequence::instruction_width(op);

      opcode arg1 = 0;
      opcode arg2 = 0;

      switch(width) {
      case 1:
        // nothing, done.
        break;
      case 2:
        if(ip >= total_) {
          fail("truncated instruction sequence", ip);
          return false;
        }

        obj = try_as<Fixnum>(ops_->at(ip++));
        if(!obj) {
          fail("corrupt instruction sequence", ip);
          return false;
        }
        arg1 = obj->to_native();
        break;

      case 3:
        if(ip >= total_) {
          fail("truncated instruction sequence", ip);
          return false;
        }

        obj = try_as<Fixnum>(ops_->at(ip++));
        if(!obj) {
          fail("corrupt instruction sequence", ip);
          return false;
        }

        arg1 = obj->to_native();

        if(ip >= total_) {
          fail("truncated instruction sequence", ip);
          return false;
        }

        obj = try_as<Fixnum>(ops_->at(ip++));
        if(!obj) {
          fail("corrupt instruction sequence", ip);
          return false;
        }

        arg2 = obj->to_native();
        break;

      default:
        fail("invalid instruction", ip);
        return false;
      }

      int read=0, write=0;

      int effect = stack_difference(op, arg1, arg2, &read, &write);

      // Check for under read
      if(sp - read < 0) {
        fail("stack underflow on read", ip);
        return false;
      }

      // Apply the total effect to propagate it.
      sp += effect;
      if(sp < 0) {
        fail("stack underflow on effect", ip);
        return false;
      }

      // Make sure we don't use more than the declared stack size.
      if(sp > max_stack_allowed_) {
        fail("stack overflow", ip);
        return false;
      }

      // Keep track of the max stack depth seen
      if(sp > max_stack_seen_) max_stack_seen_ = sp;

      switch(op) {
      case InstructionSequence::insn_push_local:
      case InstructionSequence::insn_set_local:
        if((native_int)arg1 < 0 || (native_int)arg1 >= locals_) {
          fail("invalid local variable access", ip);
          return false;
        }
        break;
      case InstructionSequence::insn_goto:
        if((native_int)arg1 < 0 || (native_int)arg1 >= total_) {
          fail("invalid goto location", ip);
          return false;
        }

        // Only handle forward branches.
        if((int)arg1 > ip) {
          ip = (int)arg1;
        } else {
          return true;
        }
        break;
      case InstructionSequence::insn_push_stack_local:
      case InstructionSequence::insn_set_stack_local:
        if((int)arg1 > max_stack_local_) {
          max_stack_local_ = (int)arg1;
        }
        break;
      case InstructionSequence::insn_goto_if_false:
      case InstructionSequence::insn_goto_if_true:
      case InstructionSequence::insn_setup_unwind:
        if((native_int)arg1 < 0 || (native_int)arg1 >= total_) {
          fail("invalid goto location", ip);
          return false;
        }

        if((int)arg1 > ip) {
          ips.push_back(Section(sp, arg1));
        }

        break;
      case InstructionSequence::insn_ret:
      case InstructionSequence::insn_raise_exc:
      case InstructionSequence::insn_raise_return:
      case InstructionSequence::insn_ensure_return:
      case InstructionSequence::insn_raise_break:
      case InstructionSequence::insn_reraise:
        return true;
      }

      // Detect falling off the end of the stream
      if(ip >= total_) {
        fail("unterminated instruction sequence", ip);
        return false;
      }
    }
  }
Пример #30
0
  bool BytecodeVerification::verify(STATE) {
    // Do this setup here instead of the constructor so we can do
    // some validation of the CompiledCode's fields we read them.

    // Double check the method itself, since it might be a nil
    if(!kind_of<CompiledCode>(method_)) {
      fail("invalid method", -1);
      return false;
    }

    if(Fixnum* fix = try_as<Fixnum>(method_->local_count())) {
      locals_ = fix->to_native();
    } else {
      fail("method not initialized properly", -1);
      return false;
    }

    InstructionSequence* iseq = try_as<InstructionSequence>(method_->iseq());
    if(!iseq) {
      fail("method not initialized properly", -1);
      return false;
    }

    if(Tuple* tup = try_as<Tuple>(iseq->opcodes())) {
      ops_ = tup;
    } else {
      fail("method not initialized properly", -1);
      return false;
    }

    if(Fixnum* fix = try_as<Fixnum>(method_->stack_size())) {
      max_stack_allowed_ = fix->to_native();
    } else {
      fail("method not initialized properly", -1);
      return false;
    }

    if(Fixnum* fix = try_as<Fixnum>(method_->splat())) {
      if(fix->to_native() >= locals_) {
        fail("invalid splat position", -1);
        return false;
      }
    }

    Fixnum* tot = try_as<Fixnum>(method_->total_args());
    Fixnum* req = try_as<Fixnum>(method_->required_args());
    Fixnum* post = try_as<Fixnum>(method_->post_args());

    if(!tot || !req || !post) {
      fail("method not initialized properly (missing arg counts)", -1);
      return false;
    }

    if(tot->to_native() > locals_) {
      fail("more arguments than local slots", -1);
      return false;
    }

    if(req->to_native() > tot->to_native()) {
      fail("more required arguments than total", -1);
      return false;
    }

    if(post->to_native() > req->to_native()) {
      fail("more post arguments than required", -1);
      return false;
    }

    if(post->to_native() > tot->to_native()) {
      fail("more post arguments than total", -1);
      return false;
    }

    total_ = ops_->num_fields();
    stack_ = new int32_t[total_];

    for(native_int i = 0; i < total_; i++) {
      stack_[i] = -1;
    }

    std::list<Section> ips;
    ips.push_back(Section(0, 0));

    while(!ips.empty()) {
      Section& section = ips.front();

      int ip = section.ip;
      int sp = section.sp;

      ips.pop_front();

      if(!verify_from(state, sp, ip, ips)) return false;
    }

    // Now, check there is a enough space for the stack locals.
    if(max_stack_seen_ + max_stack_local_ >= max_stack_allowed_) {
      fail("not enough space for stack locals", -1);
      return false;
    }

    return true;
  }