示例#1
0
            void NServiceControl::toStruct(_NServiceControl & input)
            {
                memset(&input, 0, sizeof(_NServiceControl));

                getServiceName().copy(input.ServiceName, getServiceName().length());
                getFunctionName().copy(input.FunctionName, getFunctionName().length());
            }
示例#2
0
Checksum Scenario::load(const string &path) {
    Checksum scenarioChecksum;
	try {
		scenarioChecksum.addFile(path);
		checksumValue.addFile(path);

		string name= cutLastExt(lastDir(path));
		Logger::getInstance().add("Scenario: " + formatString(name), true);

		//parse xml
		XmlTree xmlTree;
		xmlTree.load(path);
		const XmlNode *scenarioNode= xmlTree.getRootNode();
		const XmlNode *scriptsNode= scenarioNode->getChild("scripts");

		for(int i= 0; i<scriptsNode->getChildCount(); ++i){
			const XmlNode *scriptNode = scriptsNode->getChild(i);

			scripts.push_back(Script(getFunctionName(scriptNode), scriptNode->getText()));
		}
	}
	//Exception handling (conversions and so on);
	catch(const exception &e) {
		SystemFlags::OutputDebug(SystemFlags::debugError,"In [%s::%s Line: %d] Error [%s]\n",__FILE__,__FUNCTION__,__LINE__,e.what());
		throw runtime_error("Error: " + path + "\n" + e.what());
	}

	return scenarioChecksum;
}
示例#3
0
// isCrtStartupAlloc - Determines whether the memory leak was generated from crt startup code.
// This is not an actual memory leaks as it is freed by crt after the VLD object has been destroyed.
//
//  Return Value:
//
//    true if isCrtStartupModule for any callstack frame returns true.
//
bool CallStack::isCrtStartupAlloc()
{
    if (m_status & CALLSTACK_STATUS_STARTUPCRT) {
        return true;
    } else if (m_status & CALLSTACK_STATUS_NOTSTARTUPCRT) {
        return false;
    }

    IMAGEHLP_LINE64  sourceInfo = { 0 };
    sourceInfo.SizeOfStruct = sizeof(IMAGEHLP_LINE64);

    BYTE symbolBuffer[sizeof(SYMBOL_INFO) + MAX_SYMBOL_NAME_SIZE] = { 0 };
    CriticalSectionLocker<DbgHelp> locker(g_DbgHelp);

    // Iterate through each frame in the call stack.
    for (UINT32 frame = 0; frame < m_size; frame++) {
        // Try to get the source file and line number associated with
        // this program counter address.
        SIZE_T programCounter = (*this)[frame];
        DWORD64 displacement64;
        LPCWSTR functionName = getFunctionName(programCounter, displacement64, (SYMBOL_INFO*)&symbolBuffer, locker);

        m_status |= isCrtStartupFunction(functionName);
        if (m_status & CALLSTACK_STATUS_STARTUPCRT) {
            return true;
        } else if (m_status & CALLSTACK_STATUS_NOTSTARTUPCRT) {
            return false;
        }
    }

    m_status |= CALLSTACK_STATUS_NOTSTARTUPCRT;
    return false;
}
示例#4
0
void LuaMapBridge::setBlock(const int & x, const int & y, BlockType type){
	lua_getglobal(this->state, getFunctionName(type).c_str());
	lua_pushinteger(this->state, x);
	lua_pushinteger(this->state, y);

	Error(lua_pcall(this->state, 2, 0, 0), "Set Block");
}
示例#5
0
zstring FunctionItem::show() const
{
  std::ostringstream lRes;
  lRes << getFunctionName()->getStringValue();
  if (!isInline())
    lRes << "#" << getArity() << " (" << theFunctionItemInfo->theLoc << ")";
  return lRes.str();
}
示例#6
0
   void ExceptionLocation::dump(ostream& s) const
      throw()
   { 
      s << getFileName() << ":" 
#ifdef __FUNCTION__
        << getFunctionName() << ":" 
#endif
        << getLineNumber(); 
   }
示例#7
0
bool CReactionInterface::createMetabolites()
{
  bool created = mChemEqI.createNonExistingMetabs();

  // Update the parameter mapping to assure that the new names match.
  if (created)
    setFunctionAndDoMapping(getFunctionName());

  return created;
}
示例#8
0
	void GrfAutoexpand::compileCpp(CppCompilerEnvironment& theCompilerEnvironment) const {
		CW_BODY_INDENT << "// warning: the behaviour of 'autoexpand' may vary of the interpreted mode";
		CW_BODY_ENDL;
		CW_BODY_INDENT << "CGRuntime::" << getFunctionName() << "(";
		_pFileName->compileCppString(theCompilerEnvironment);
		CW_BODY_STREAM << ", ";
		_pClass->compileCpp(theCompilerEnvironment);
		CW_BODY_STREAM << ");";
		CW_BODY_ENDL;
	}
示例#9
0
// XED callback function to get a symbol from an address
static int addressToSymbol(xed_uint64_t address,
                           char *symbol_buffer,
                           xed_uint32_t buffer_length,
                           xed_uint64_t *offset,
                           void *context) {
  auto& memoVal = addressToSymbolMemo[address];
  if (memoVal != nullptr) {
    strncpy(symbol_buffer, memoVal, buffer_length - 1);
    symbol_buffer[buffer_length - 1] = '\0';
    *offset = 0;
    return 1;
  }

  char **symbolTable = backtrace_symbols((void **)&address, 1);
  if (!symbolTable) {
    return 0;
  }
  char *backtraceName = symbolTable[0];
  char *mangledName = getFunctionName(backtraceName);
  free(symbolTable);
  if (!mangledName) {
    return 0;
  }

  int status;
  char *demangledName = abi::__cxa_demangle(mangledName, NULL, NULL, &status);
  char *methodName = NULL;
  if (status == 0) {
    free(mangledName);
    methodName = getMethodName(demangledName);
    free(demangledName);
  } else if (status == -2) {
    methodName = mangledName;
  } else {
    free(mangledName);
  }

  if (methodName) {
    strncpy(symbol_buffer, methodName, buffer_length - 1);
    symbol_buffer[buffer_length - 1] = '\0';
    memoVal = methodName;
  } else {
    return 0;
  }

  *offset = 0;
  return 1;
}
示例#10
0
文件: callstack.cpp 项目: viknash/vld
// isCrtStartupAlloc - Determines whether the memory leak was generated from crt startup code.
// This is not an actual memory leaks as it is freed by crt after the VLD object has been destroyed.
//
//  Return Value:
//
//    true if isCrtStartupModule for any callstack frame returns true.
//
bool CallStack::isCrtStartupAlloc()
{
    if (m_status & CALLSTACK_STATUS_STARTUPCRT) {
        return true;
    } else if (m_status & CALLSTACK_STATUS_NOTSTARTUPCRT) {
        return false;
    }

    IMAGEHLP_LINE64  sourceInfo = { 0 };
    sourceInfo.SizeOfStruct = sizeof(IMAGEHLP_LINE64);

    BYTE symbolBuffer[sizeof(SYMBOL_INFO) + MAX_SYMBOL_NAME_SIZE] = { 0 };
    CriticalSectionLocker<DbgHelp> locker(g_DbgHelp);

    // Iterate through each frame in the call stack.
    for (UINT32 frame = 0; frame < m_size; frame++) {
        // Try to get the source file and line number associated with
        // this program counter address.
        SIZE_T programCounter = (*this)[frame];
        BOOL             foundline = FALSE;
        DWORD            displacement = 0;
        DbgTrace(L"dbghelp32.dll %i: SymGetLineFromAddrW64\n", GetCurrentThreadId());
        foundline = g_DbgHelp.SymGetLineFromAddrW64(g_currentProcess, programCounter, &displacement, &sourceInfo);

        if (foundline) {
            DWORD64 displacement64;
            LPCWSTR functionName = getFunctionName(programCounter, displacement64, (SYMBOL_INFO*)&symbolBuffer, locker);
            if (beginWith(functionName, wcslen(functionName), L"`dynamic initializer for '")) {
                break;
            }

            if (isCrtStartupModule(sourceInfo.FileName)) {
                m_status |= CALLSTACK_STATUS_STARTUPCRT;
                return true;
            }
        }
    }

    m_status |= CALLSTACK_STATUS_NOTSTARTUPCRT;
    return false;
}
示例#11
0
void CReactionInterface::printDebug() const
{
  std::cout << "Reaction interface   " << std::endl;
  std::cout << "  Function: " << getFunctionName() << std::endl;
  std::cout << "  ChemEq:   " << getChemEqString() << std::endl;

  size_t i, imax = size();

  for (i = 0; i < imax; ++i)
    {
      std::cout << "    ---  " << i << ": " << getParameterName(i)
                << ", vector: " << isVector(i) << " local: " << isLocalValue(i)
                << ", value: " << mValues[i] << std::endl;

      size_t j, jmax = mNameMap[i].size();

      for (j = 0; j < jmax; ++j)
        std::cout << "            " << mNameMap[i][j] << std::endl;
    }

  std::cout << std::endl;
}
示例#12
0
void showParametersVNS(pVNS *vns)/*{{{*/
{
	printf("***VNS PARAMETERS***\n");
	printf("RUNS = %d\n", vns->RUN);
	printf("DIM = %d\n", vns->DIM);
	printf("FUNCTION = %s\n", getFunctionName(vns->FUNCTION));
	printf("METHOD = %d\n", vns->METHOD);
	printf("****************\n");
	printf("KMAX = %d\n",vns->KMAX);
	printf("TMAX = %d\n", vns->TMAX);
	printf("Q = %f\n", vns->Q);
	printf("RADII = %f\n", vns->RADII);
	printf("RADII_T_FLAG = %d\n", vns->RADII_T_FLAG);
	printf("METRIC P = %d\n", vns->P);
	printf("VNS_POP = %d\n", vns->VNS_POP);
	printf("ECO_STEP = %d\n", vns->ECO_STEP);
	printf("EVO_STEP = %d\n", vns->EVO_STEP);
	printf("****************\n");
	printf("***HOOKE AND JEEVES PARAMETERS***\n");
	printf("AVAL_MAX = %d\n", vns->AVAL_MAX);
	printf("RHO = %f\n", vns->RHO);
	printf("EPSILON = %f\n", vns->EPSILON);
	printf("****************\n");
}/*}}}*/
void saveTreeToXml( TiXmlElement* pElem, shared_ptr<MathObj> obj, bool isNewRow )
{
    if( isNewRow ) {
        TiXmlElement* element (new TiXmlElement( "mrow" ));
        pElem->LinkEndChild( element );
        pElem = element;
        isNewRow = false;
    }

    std::string objType = typeid( *obj ).name();

    if( objType == "class ParamObj" ) 
    {
        std::string val = static_pointer_cast< ParamObj >( obj )->GetVal();
		if( val[0] < '0' || val[0] > '9' ) // если значение начинается с буквы, то - идентификатор 
        {
            linkNewElem( pElem, "mi", val.c_str() );
        }
        else {
            linkNewElem( pElem, "mn", val.c_str() );
        }
    }
    else if( objType == "class FormulaObj" )
    {
        shared_ptr<FormulaObj> node = static_pointer_cast< FormulaObj >( obj );
        TNodeType type = node->GetType();
        std::vector<shared_ptr<MathObj>>::iterator it = node->params.begin( );
        std::vector<shared_ptr<MathObj>>::const_iterator itLast = node->params.end( ) - 1;
        TiXmlElement* element;

        switch( type )
        {
        case NT_PLUS:
            for( it; it != itLast; ++it )
            {
                saveTreeToXml( pElem, *it, isNewRow );
                linkNewElem( pElem, "mo", "+" );
            }
            saveTreeToXml( pElem, *it, isNewRow );
            break;

        case NT_UMINUS:
            linkNewElem( pElem, "mo", "-" );
            saveTreeToXml( pElem, *it, isNewRow );
            break;
            
        case NT_MINUS:
            saveTreeToXml( pElem, *it, isNewRow );
            linkNewElem( pElem, "mo", "-" );
            saveTreeToXml( pElem, *itLast, isNewRow );
            break;

        case NT_MULTNCM: // TODO поправить в будущем, пока как обычное умножение
            for( it; it != itLast; ++it )
            {
                saveTreeToXml( pElem, *it, isNewRow );
            }
            saveTreeToXml( pElem, *it, isNewRow );
            break;

        case NT_DIV:
            element = (new TiXmlElement( "mfrac" ));
            pElem->LinkEndChild( element );
            saveTreeToXml( element, *it, true );
            saveTreeToXml( element, *itLast, true );
            break;

        case NT_POW:
            element = (new TiXmlElement( "msup" ));
            pElem->LinkEndChild( element );
            saveTreeToXml( element, *it, false );
            saveTreeToXml( element, *itLast, false );
            break;

        case NT_ROOT:
            if( itLast == it )
            {
				element = (new TiXmlElement("msqrt"));
                pElem->LinkEndChild( element );
                saveTreeToXml( element, *it, false );
            }
            break;

        case NT_MULTCM:
            for( it; it != itLast; ++it )
            {
                saveTreeToXml( pElem, *it, isNewRow );
            }
            saveTreeToXml( pElem, *it, isNewRow );
            break;

        case NT_EQUAL:
            saveTreeToXml( pElem, *it, isNewRow );
            linkNewElem( pElem, "mo", "=" );
            saveTreeToXml( pElem, *itLast, isNewRow );
            break;

        case NT_LESS:
            saveTreeToXml( pElem, *it, isNewRow );
            linkNewElem( pElem, "mo", "<" );
            saveTreeToXml( pElem, *itLast, isNewRow );
            break;

        case NT_GREAT:
            saveTreeToXml( pElem, *it, isNewRow );
            linkNewElem( pElem, "mo", ">" );
            saveTreeToXml( pElem, *itLast, isNewRow );
            break;

        case NT_NEQUAL:
            saveTreeToXml( pElem, *it, isNewRow );
            linkNewElem( pElem, "mo", "≠" );
            saveTreeToXml( pElem, *itLast, isNewRow );
            break;

        case NT_LESSEQ:
            saveTreeToXml( pElem, *it, isNewRow );
            linkNewElem( pElem, "mo", "\\leq" );
            saveTreeToXml( pElem, *itLast, isNewRow );
            break;

        case NT_GREATEQ:
            saveTreeToXml( pElem, *it, isNewRow );
            linkNewElem( pElem, "mo", "\\geq" );
            saveTreeToXml( pElem, *itLast, isNewRow );
            break;

        case NT_APPROX:
            saveTreeToXml( pElem, *it, isNewRow );
            linkNewElem( pElem, "mo", "≈" );
            saveTreeToXml( pElem, *itLast, isNewRow );
            break;

        case NT_PLUSMINUS:
            saveTreeToXml( pElem, *it, isNewRow );
            linkNewElem( pElem, "mo", "±" );
            saveTreeToXml( pElem, *itLast, isNewRow );
            break;

		case NT_SUM:
		case NT_PROD:
		{
			element = new TiXmlElement( "munderover" );
			pElem->LinkEndChild( element );
			TiXmlElement* sign = new TiXmlElement( "mo" );
			if( type == NT_PROD ) {
				sign->LinkEndChild( new TiXmlText( "∏" ) );
			} else {
				sign->LinkEndChild( new TiXmlText( "∑" ) );
			}
			element->LinkEndChild( sign );
			saveTreeToXml( element, *it, true );
			saveTreeToXml( element, *( ++it ), true );
			saveTreeToXml( pElem, *itLast, isNewRow );
		}
			break;
		case NT_SIN:
		case NT_COS:
		case NT_TAN:
		case NT_COT:
			linkNewElem( pElem, "mo", getFunctionName( type ).c_str() );
			saveTreeToXml( pElem, *it, false );
			break;
        default:
            std::cerr << "Ошибка, не поддерживаемый (пока) тип оператора, код: " << type << std::endl;
        }
    }
}
void CallReplace::instrument(){
    uint32_t temp32;
    uint64_t temp64;

    LineInfoFinder* lineInfoFinder = NULL;
    if (hasLineInformation()){
        lineInfoFinder = getLineInfoFinder();
    }

    InstrumentationPoint* p = addInstrumentationPoint(getProgramEntryBlock(), programEntry, InstrumentationMode_tramp, FlagsProtectionMethod_full, InstLocation_prior);
    ASSERT(p);
    if (!p->getInstBaseAddress()){
        PRINT_ERROR("Cannot find an instrumentation point at the exit function");
    }

    p = addInstrumentationPoint(getProgramExitBlock(), programExit, InstrumentationMode_tramp, FlagsProtectionMethod_full, InstLocation_prior);
    ASSERT(p);
    if (!p->getInstBaseAddress()){
        PRINT_ERROR("Cannot find an instrumentation point at the exit function");
    }

    uint64_t siteIndex = reserveDataOffset(sizeof(uint32_t));
    programEntry->addArgument(siteIndex);

    Vector<X86Instruction*> myInstPoints;
    Vector<uint32_t> myInstList;
    Vector<LineInfo*> myLineInfos;
    for (uint32_t i = 0; i < getNumberOfExposedInstructions(); i++){
        X86Instruction* instruction = getExposedInstruction(i);
        ASSERT(instruction->getContainer()->isFunction());
        Function* function = (Function*)instruction->getContainer();
        
        if (instruction->isFunctionCall()){
            Symbol* functionSymbol = getElfFile()->lookupFunctionSymbol(instruction->getTargetAddress());

            if (functionSymbol){
                //PRINT_INFOR("looking for function %s", functionSymbol->getSymbolName());
                uint32_t funcIdx = searchFileList(functionList, functionSymbol->getSymbolName());
                if (funcIdx < (*functionList).size()){
                    BasicBlock* bb = function->getBasicBlockAtAddress(instruction->getBaseAddress());
                    ASSERT(bb->containsCallToRange(0,-1));
                    ASSERT(instruction->getSizeInBytes() == Size__uncond_jump);

                    myInstPoints.append(instruction);
                    myInstList.append(funcIdx);
                    LineInfo* li = NULL;
                    if (lineInfoFinder){
                        li = lineInfoFinder->lookupLineInfo(bb);
                    }
                    myLineInfos.append(li);
                }
            }
        } 
    }
    ASSERT(myInstPoints.size() == myInstList.size());
    ASSERT(myLineInfos.size() == myInstList.size());

    uint64_t fileNames = reserveDataOffset(sizeof(char*) * myInstList.size());
    uint64_t lineNumbers = reserveDataOffset(sizeof(uint32_t) * myInstList.size());
    for (uint32_t i = 0; i < myInstList.size(); i++){
        uint32_t line = 0;
        char* fname = NOSTRING;
        if (myLineInfos[i]){
            line = myLineInfos[i]->GET(lr_line);
            fname = myLineInfos[i]->getFileName();
        }
        uint64_t filenameaddr = getInstDataAddress() + reserveDataOffset(strlen(fname) + 1);
        initializeReservedData(getInstDataAddress() + fileNames + i*sizeof(char*), sizeof(char*), &filenameaddr);
        initializeReservedData(filenameaddr, strlen(fname), fname);
        initializeReservedData(getInstDataAddress() + lineNumbers + i*sizeof(uint32_t), sizeof(uint32_t), &line);
    }
    programEntry->addArgument(fileNames);
    programEntry->addArgument(lineNumbers);

    for (uint32_t i = 0; i < myInstPoints.size(); i++){
        PRINT_INFOR("(site %d) %#llx: replacing call %s -> %s in function %s", i, myInstPoints[i]->getBaseAddress(), getFunctionName(myInstList[i]), getWrapperName(myInstList[i]), myInstPoints[i]->getContainer()->getName());
        InstrumentationPoint* pt = addInstrumentationPoint(myInstPoints[i], functionWrappers[myInstList[i]], InstrumentationMode_tramp, FlagsProtectionMethod_none, InstLocation_replace);
        if (getElfFile()->is64Bit()){
            pt->addPrecursorInstruction(X86InstructionFactory64::emitMoveRegToMem(X86_REG_CX, getInstDataAddress() + getRegStorageOffset()));
            pt->addPrecursorInstruction(X86InstructionFactory64::emitMoveImmToReg(i, X86_REG_CX));
            pt->addPrecursorInstruction(X86InstructionFactory64::emitMoveRegToMem(X86_REG_CX, getInstDataAddress() + siteIndex));
            pt->addPrecursorInstruction(X86InstructionFactory64::emitMoveMemToReg(getInstDataAddress() + getRegStorageOffset(), X86_REG_CX, true));
        } else {
            pt->addPrecursorInstruction(X86InstructionFactory32::emitMoveRegToMem(X86_REG_CX, getInstDataAddress() + getRegStorageOffset()));
            pt->addPrecursorInstruction(X86InstructionFactory32::emitMoveImmToReg(i, X86_REG_CX));
            pt->addPrecursorInstruction(X86InstructionFactory32::emitMoveRegToMem(X86_REG_CX, getInstDataAddress() + siteIndex));
            pt->addPrecursorInstruction(X86InstructionFactory32::emitMoveMemToReg(getInstDataAddress() + getRegStorageOffset(), X86_REG_CX));            
        }
    }
}
示例#15
0
void Decompiler::writeInstruction(Common::WriteStream &out, const Instruction* instruction, size_t indent) {
	switch (instruction->opcode) {
		case kOpcodeCONST: {
			const Variable *v = instruction->variables[0];
			writeIndent(out, indent);
			out.writeString(getVariableTypeName(v->type) + " " + formatVariableName(v) + " = " + formatInstructionData(*instruction) + ";\n");

			break;
		}

		case kOpcodeACTION: {
			unsigned int paramCount = instruction->args[1];

			writeIndent(out, indent);

			if (instruction->variables.size() > paramCount) {
				const Variable *ret = instruction->variables.back();
				out.writeString(getVariableTypeName(ret->type, _ncs->getGame()) + " " + formatVariableName(ret) + " = ");
			}

			out.writeString(getFunctionName(_ncs->getGame(), instruction->args[0]));
			out.writeString("(");
			for (unsigned int i = 0; i < paramCount; ++i) {
				out.writeString(formatVariableName(instruction->variables[i]));
				if (i < paramCount - 1)
					out.writeString(", ");
			}
			out.writeString(");\n");

			break;
		}

		case kOpcodeCPDOWNBP:
		case kOpcodeCPDOWNSP:
		case kOpcodeCPTOPBP:
		case kOpcodeCPTOPSP: {
			const Variable *v1 = instruction->variables[0];
			const Variable *v2 = instruction->variables[1];

			writeIndent(out, indent);
			out.writeString(getVariableTypeName(v2->type, _ncs->getGame()) + " " + formatVariableName(v2) + " = " + formatVariableName(v1) + ";\n");

			break;
		}

		case kOpcodeLOGAND: {
			const Variable *v1 = instruction->variables[0];
			const Variable *v2 = instruction->variables[1];
			const Variable *result = instruction->variables[2];

			writeIndent(out, indent);
			out.writeString(
					getVariableTypeName(result->type, _ncs->getGame()) + " " +
					formatVariableName(result) + " = " +
					formatVariableName(v1) + " && " + formatVariableName(v2) + ";\n"
			);

			break;
		}

		case kOpcodeLOGOR: {
			const Variable *v1 = instruction->variables[0];
			const Variable *v2 = instruction->variables[1];
			const Variable *result = instruction->variables[2];

			writeIndent(out, indent);
			out.writeString(
					getVariableTypeName(result->type, _ncs->getGame()) + " " +
					formatVariableName(result) + " = " +
					formatVariableName(v1) + " || " + formatVariableName(v2) + ";\n"
			);

			break;
		}

		case kOpcodeEQ: {
			const Variable *v1 = instruction->variables[0];
			const Variable *v2 = instruction->variables[1];
			const Variable *result = instruction->variables[2];

			writeIndent(out, indent);
			out.writeString(
					getVariableTypeName(result->type, _ncs->getGame()) + " " +
					formatVariableName(result) + " = " +
					formatVariableName(v1) + " == " + formatVariableName(v2) + ";\n"
			);


			break;
		}

		case kOpcodeLEQ: {
			const Variable *v1 = instruction->variables[0];
			const Variable *v2 = instruction->variables[1];
			const Variable *result = instruction->variables[2];

			writeIndent(out, indent);
			out.writeString(
					getVariableTypeName(result->type, _ncs->getGame()) + " " +
					formatVariableName(result) + " = " +
					formatVariableName(v1) + " <= " + formatVariableName(v2) + ";\n"
			);

			break;
		}

		case kOpcodeLT: {
			const Variable *v1 = instruction->variables[0];
			const Variable *v2 = instruction->variables[1];
			const Variable *result = instruction->variables[2];

			writeIndent(out, indent);
			out.writeString(
					getVariableTypeName(result->type, _ncs->getGame()) + " " +
					formatVariableName(result) + " = " +
					formatVariableName(v1) + " < " + formatVariableName(v2) + ";\n"
			);

			break;
		}

		case kOpcodeGEQ: {
			const Variable *v1 = instruction->variables[0];
			const Variable *v2 = instruction->variables[1];
			const Variable *result = instruction->variables[2];

			writeIndent(out, indent);
			out.writeString(
					getVariableTypeName(result->type, _ncs->getGame()) + " " +
					formatVariableName(result) + " = " +
					formatVariableName(v1) + " >= " + formatVariableName(v2) + ";\n"
			);

			break;
		}

		case kOpcodeGT: {
			const Variable *v1 = instruction->variables[0];
			const Variable *v2 = instruction->variables[1];
			const Variable *result = instruction->variables[2];

			writeIndent(out, indent);
			out.writeString(
					getVariableTypeName(result->type, _ncs->getGame()) + " " +
					formatVariableName(result) + " = " +
					formatVariableName(v1) + " > " + formatVariableName(v2) + ";\n"
			);

			break;
		}

		case kOpcodeNOT: {
			const Variable *v = instruction->variables[0];
			const Variable *result = instruction->variables[1];

			writeIndent(out, indent);
			out.writeString(
					getVariableTypeName(result->type, _ncs->getGame()) + " " +
					formatVariableName(result) + " = " +
					"!" + formatVariableName(v) + ";\n"
			);

			break;
		}

		case kOpcodeRSADD: {
			const Variable *v = instruction->variables[0];

			writeIndent(out, indent);
			out.writeString(
					getVariableTypeName(v->type, _ncs->getGame()) + " " +
					formatVariableName(v) + " = "
			);

			switch (v->type) {
				case kTypeString:
					out.writeString("\"\"");
					break;
				case kTypeInt:
					out.writeString("0");
					break;
				case kTypeFloat:
					out.writeString("0.0");
					break;

				default:
					// TODO: No idea how empty objects or engine types are intialized.
					out.writeString("0");
					break;
			}

			out.writeString(";\n");

			break;
		}

		// TODO: Not all necessary instruction are implemented here

		default:
			break;
	}
}
示例#16
0
文件: callstack.cpp 项目: viknash/vld
// dump - Dumps a nicely formatted rendition of the CallStack, including
//   symbolic information (function names and line numbers) if available.
//
//   Note: The symbol handler must be initialized prior to calling this
//     function.
//
//  - showinternalframes (IN): If true, then all frames in the CallStack will be
//      dumped. Otherwise, frames internal to the heap will not be dumped.
//
//  Return Value:
//
//    None.
//
void CallStack::dump(BOOL showInternalFrames, UINT start_frame) const
{
    // The stack was dumped already
    if (m_resolved)
    {
        dumpResolved();
        return;
    }

    if (m_status & CALLSTACK_STATUS_INCOMPLETE) {
        // This call stack appears to be incomplete. Using StackWalk64 may be
        // more reliable.
        Report(L"    HINT: The following call stack may be incomplete. Setting \"StackWalkMethod\"\n"
            L"      in the vld.ini file to \"safe\" instead of \"fast\" may result in a more\n"
            L"      complete stack trace.\n");
    }

    IMAGEHLP_LINE64  sourceInfo = { 0 };
    sourceInfo.SizeOfStruct = sizeof(IMAGEHLP_LINE64);

    // Use static here to increase performance, and avoid heap allocs.
    // It's thread safe because of g_heapMapLock lock.
    static WCHAR stack_line[MAXREPORTLENGTH + 1] = L"";
    bool isPrevFrameInternal = false;
    CriticalSectionLocker<DbgHelp> locker(g_DbgHelp);

    // Iterate through each frame in the call stack.
    for (UINT32 frame = start_frame; frame < m_size; frame++)
    {
        // Try to get the source file and line number associated with
        // this program counter address.
        SIZE_T programCounter = (*this)[frame];
        BOOL             foundline = FALSE;
        DWORD            displacement = 0;
        DbgTrace(L"dbghelp32.dll %i: SymGetLineFromAddrW64\n", GetCurrentThreadId());
        foundline = g_DbgHelp.SymGetLineFromAddrW64(g_currentProcess, programCounter, &displacement, &sourceInfo, locker);

        bool isFrameInternal = false;
        if (foundline && !showInternalFrames) {
            if (isInternalModule(sourceInfo.FileName))
            {
                // Don't show frames in files internal to the heap.
                isFrameInternal = true;
            }
        }

        // show one allocation function for context
        if (!isFrameInternal && isPrevFrameInternal)
            Print(stack_line);
        isPrevFrameInternal = isFrameInternal;

        DWORD64 displacement64;
        BYTE symbolBuffer[sizeof(SYMBOL_INFO) + MAX_SYMBOL_NAME_SIZE];
        LPCWSTR functionName = getFunctionName(programCounter, displacement64, (SYMBOL_INFO*)&symbolBuffer, locker);

        if (!foundline)
            displacement = (DWORD)displacement64;
        DWORD NumChars = resolveFunction(programCounter, foundline ? &sourceInfo : NULL,
            displacement, functionName, stack_line, _countof(stack_line));
        UNREFERENCED_PARAMETER(NumChars);

        if (!isFrameInternal)
            Print(stack_line);
    }
}
示例#17
0
文件: callstack.cpp 项目: viknash/vld
// Resolve - Creates a nicely formatted rendition of the CallStack, including
//   symbolic information (function names and line numbers) if available. and
//   saves it for later retrieval. This is almost identical to Callstack::dump above.
//
//   Note: The symbol handler must be initialized prior to calling this
//     function.
//
//  - showInternalFrames (IN): If true, then all frames in the CallStack will be
//      dumped. Otherwise, frames internal to the heap will not be dumped.
//
//  Return Value:
//
//    None.
//
int CallStack::resolve(BOOL showInternalFrames)
{
    if (m_resolved)
    {
        // already resolved, no need to do it again
        // resolving twice may report an incorrect module for the stack frames
        // if the memory was leaked in a dynamic library that was already unloaded.
        return 0;
    }

    if (m_status & CALLSTACK_STATUS_STARTUPCRT) {
        // there is no need to resolve a leak that will not be reported
        return 0;
    }

    if (m_status & CALLSTACK_STATUS_INCOMPLETE) {
        // This call stack appears to be incomplete. Using StackWalk64 may be
        // more reliable.
        Report(L"    HINT: The following call stack may be incomplete. Setting \"StackWalkMethod\"\n"
            L"      in the vld.ini file to \"safe\" instead of \"fast\" may result in a more\n"
            L"      complete stack trace.\n");
    }

    int unresolvedFunctionsCount = 0;
    IMAGEHLP_LINE64  sourceInfo = { 0 };
    sourceInfo.SizeOfStruct = sizeof(IMAGEHLP_LINE64);

    bool skipStartupLeaks = !!(g_vld.GetOptions() & VLD_OPT_SKIP_CRTSTARTUP_LEAKS);

    // Use static here to increase performance, and avoid heap allocs.
    // It's thread safe because of g_heapMapLock lock.
    static WCHAR stack_line[MAXREPORTLENGTH + 1] = L"";
    bool isPrevFrameInternal = false;
    bool isDynamicInitializer = false;
    DWORD NumChars = 0;
    CriticalSectionLocker<DbgHelp> locker(g_DbgHelp);

    const size_t max_line_length = MAXREPORTLENGTH + 1;
    m_resolvedCapacity = m_size * max_line_length;
    const size_t allocedBytes = m_resolvedCapacity * sizeof(WCHAR);
    m_resolved = new WCHAR[m_resolvedCapacity];
    if (m_resolved) {
        ZeroMemory(m_resolved, allocedBytes);
    }

    // Iterate through each frame in the call stack.
    for (UINT32 frame = 0; frame < m_size; frame++)
    {
        // Try to get the source file and line number associated with
        // this program counter address.
        SIZE_T programCounter = (*this)[frame];
        DWORD            displacement = 0;

        // It turns out that calls to SymGetLineFromAddrW64 may free the very memory we are scrutinizing here
        // in this method. If this is the case, m_Resolved will be null after SymGetLineFromAddrW64 returns.
        // When that happens there is nothing we can do except crash.
        DbgTrace(L"dbghelp32.dll %i: SymGetLineFromAddrW64\n", GetCurrentThreadId());
        BOOL foundline = g_DbgHelp.SymGetLineFromAddrW64(g_currentProcess, programCounter, &displacement, &sourceInfo, locker);

        if (skipStartupLeaks && foundline && !isDynamicInitializer &&
            !(m_status & CALLSTACK_STATUS_NOTSTARTUPCRT) && isCrtStartupModule(sourceInfo.FileName)) {
            m_status |= CALLSTACK_STATUS_STARTUPCRT;
            delete[] m_resolved;
            m_resolved = NULL;
            m_resolvedCapacity = 0;
            m_resolvedLength = 0;
            return 0;
        }

        bool isFrameInternal = false;
        if (foundline && !showInternalFrames) {
            if (isInternalModule(sourceInfo.FileName)) {
                // Don't show frames in files internal to the heap.
                isFrameInternal = true;
            }
        }

        // show one allocation function for context
        if (NumChars > 0 && !isFrameInternal && isPrevFrameInternal) {
            m_resolvedLength += NumChars;
            if (m_resolved) {
                wcsncat_s(m_resolved, m_resolvedCapacity, stack_line, NumChars);
            }
        }
        isPrevFrameInternal = isFrameInternal;

        DWORD64 displacement64;
        BYTE symbolBuffer[sizeof(SYMBOL_INFO) + MAX_SYMBOL_NAME_SIZE];
        LPCWSTR functionName = getFunctionName(programCounter, displacement64, (SYMBOL_INFO*)&symbolBuffer, locker);

        if (skipStartupLeaks && foundline && beginWith(functionName, wcslen(functionName), L"`dynamic initializer for '")) {
            isDynamicInitializer = true;
        }

        if (!foundline)
            displacement = (DWORD)displacement64;
        NumChars = resolveFunction( programCounter, foundline ? &sourceInfo : NULL,
            displacement, functionName, stack_line, _countof( stack_line ));

        if (NumChars > 0 && !isFrameInternal) {
            m_resolvedLength += NumChars;
            if (m_resolved) {
                wcsncat_s(m_resolved, m_resolvedCapacity, stack_line, NumChars);
            }
        }
    } // end for loop

    m_status |= CALLSTACK_STATUS_NOTSTARTUPCRT;
    return unresolvedFunctionsCount;
}
示例#18
0
void printTrace()
{
	SymInitialize(GetCurrentProcess(), NULL, TRUE);

	UINT32 maxframes = 62;
	UINT_PTR myFrames[62];

	ZeroMemory(myFrames, sizeof(UINT_PTR) * maxframes);
	ULONG BackTraceHash;
	maxframes = CaptureStackBackTrace(0, maxframes, reinterpret_cast<PVOID*>(myFrames), &BackTraceHash);

	const UINT_PTR* pFrame = myFrames;
	const size_t frameSize = maxframes;

	UINT32  startIndex = 0;

	int unresolvedFunctionsCount = 0;
	IMAGEHLP_LINE  sourceInfo = { 0 };
	sourceInfo.SizeOfStruct = sizeof(IMAGEHLP_LINE);

	// Use static here to increase performance, and avoid heap allocs.
	// It's thread safe because of g_heapMapLock lock.
	static char stack_line[1024] = "";
	bool isPrevFrameInternal = false;
	DWORD NumChars = 0;

	const size_t max_line_length = 512;
	const int resolvedCapacity = 62 * max_line_length;
	const size_t allocedBytes = resolvedCapacity * sizeof(char);
	char resolved[resolvedCapacity];
	if (resolved) {
		ZeroMemory(resolved, allocedBytes);
	}
	HANDLE hProcess = GetCurrentProcess();
	int resolvedLength = 0;
	// Iterate through each frame in the call stack.
	for (UINT32 frame = 0; frame < frameSize; frame++)
	{
		if (pFrame[frame] == 0)
			break;
		// Try to get the source file and line number associated with
		// this program counter address.
		SIZE_T programCounter = pFrame[frame];

		DWORD64 displacement64;
		BYTE symbolBuffer[sizeof(SYMBOL_INFO) + 256 * sizeof(char)];
		LPCSTR functionName = getFunctionName(programCounter, displacement64, (SYMBOL_INFO*)&symbolBuffer);

		// It turns out that calls to SymGetLineFromAddrW64 may free the very memory we are scrutinizing here
		// in this method. If this is the case, m_Resolved will be null after SymGetLineFromAddrW64 returns.
		// When that happens there is nothing we can do except crash.
		DWORD            displacement = 0;

		BOOL foundline = SymGetLineFromAddr(hProcess, programCounter, &displacement, &sourceInfo);

		bool isFrameInternal = false;

		// show one allocation function for context
		if (NumChars > 0 && !isFrameInternal && isPrevFrameInternal) {
			resolvedLength += NumChars;
			if (resolved) {
				strncat_s(resolved, resolvedCapacity, stack_line, NumChars);
			}
		}
		isPrevFrameInternal = isFrameInternal;

		if (!foundline)
			displacement = (DWORD)displacement64;
		NumChars = resolveFunction(programCounter, foundline ? &sourceInfo : NULL,
			displacement, functionName, stack_line, _countof(stack_line));

		if (NumChars > 0 && !isFrameInternal) {
			resolvedLength += NumChars;
			if (resolved) {
				strncat_s(resolved, resolvedCapacity, stack_line, NumChars);
			}
		}
	} // end for loop
	printLog(resolved);

	SymCleanup(GetCurrentProcess());
	return;
}
示例#19
0
void CReactionInterface::findAndSetFunction(const std::string & newFunction)
{
  std::vector<std::string> fl = getListOfPossibleFunctions();
  size_t i, imax = fl.size();

  //no valid function?
  if (imax == 0)
    {
      setFunctionAndDoMapping("");
      return;
    }

  //first try the function provided as argument
  if (newFunction != "")
    {
      for (i = 0; i < imax; ++i)
        if (fl[i] == newFunction)
          {
            setFunctionAndDoMapping(fl[i]);
            return;
          }
    }

  //next try if the current function works
  std::string currentFunctionName = getFunctionName();

  if ("" != currentFunctionName)
    {
      for (i = 0; i < imax; ++i)
        if (fl[i] == currentFunctionName)
          {
            setFunctionAndDoMapping(fl[i]);
            return;
          }
    }

  // if not found then see if there is a best match in the list (i.e. a corresponding rev/irrev function).
  //if there is a current function try to find a related new function
  std::string s;

  if (currentFunctionName != "")
    {
      s = currentFunctionName.substr(0, currentFunctionName.find('(') - 1);

      //'-1' so as to strip off the white space before '('
      //This is purely heuristics
      for (i = 0; i < imax; i++)
        {
          if (fl[i].find(s) != std::string::npos)    // if find succeeds, the return value is likely to be 0
            //if (fl[i].find(s) >= 0) - for some reason this doesn't work
            {
              setFunctionAndDoMapping(fl[i]);
              return;
            }
        }
    }

  //try mass action next
  s = "Mass action";

  for (i = 0; i < imax; i++)
    {
      if (fl[i].find(s) != std::string::npos)    // if find succeeds, the return value is likely to be 0
        //if (fl[i].find(s) >= 0) - for some reason this doesn't work
        {
          setFunctionAndDoMapping(fl[i]);
          return;
        }
    }

  //try constant flux next
  s = "Constant flux";

  for (i = 0; i < imax; i++)
    {
      if (fl[i].find(s) != std::string::npos)    // if find succeeds, the return value is likely to be 0
        //if (fl[i].find(s) >= 0) - for some reason this doesn't work
        {
          setFunctionAndDoMapping(fl[i]);

          // If we have a reaction of the type X + Y = and the function
          // is Constant flux (reversible) we need to set the parameter v to
          // be negative to avoid negative concentrations during time course simulations.
          // Note, this fix is only done when we are assigning a default rate law.
          if (mChemEqI.getReversibility() == true &&
              mChemEqI.getListOfDisplayNames(CFunctionParameter::PRODUCT).size() == 0)
            {
              C_FLOAT64 v = - fabs(getLocalValue(0));
              setLocalValue(0, v);
            }

          return;
        }
    }

  //if everything else fails just take the first function from the list
  //this should not be reached since constant flux is a valid kinetic function for every reaction
  setFunctionAndDoMapping(fl[0]);
}
示例#20
0
/*
** Error check the functions in an expression.  Make sure all
** function names are recognized and all functions have the correct
** number of arguments.  Leave an error message in pParse->zErrMsg
** if anything is amiss.  Return the number of errors.
**
** if pIsAgg is not null and this expression is an aggregate function
** (like count(*) or max(value)) then write a 1 into *pIsAgg.
*/
int sqliteExprCheck(Parse *pParse, Expr *pExpr, int allowAgg, int *pIsAgg){
  int nErr = 0;
  if( pExpr==0 ) return 0;
  switch( pExpr->op ){
    case TK_GLOB:
    case TK_LIKE:
    case TK_FUNCTION: {
      int n = pExpr->pList ? pExpr->pList->nExpr : 0;  /* Number of arguments */
      int no_such_func = 0;       /* True if no such function exists */
      int wrong_num_args = 0;     /* True if wrong number of arguments */
      int is_agg = 0;             /* True if is an aggregate function */
      int i;
      int nId;                    /* Number of characters in function name */
      const char *zId;            /* The function name. */
      FuncDef *pDef;

      getFunctionName(pExpr, &zId, &nId);
      pDef = sqliteFindFunction(pParse->db, zId, nId, n, 0);
      if( pDef==0 ){
        pDef = sqliteFindFunction(pParse->db, zId, nId, -1, 0);
        if( pDef==0 ){
          no_such_func = 1;
        }else{
          wrong_num_args = 1;
        }
      }else{
        is_agg = pDef->xFunc==0;
      }
      if( is_agg && !allowAgg ){
        sqliteErrorMsg(pParse, "misuse of aggregate function %.*s()", nId, zId);
        nErr++;
        is_agg = 0;
      }else if( no_such_func ){
        sqliteErrorMsg(pParse, "no such function: %.*s", nId, zId);
        nErr++;
      }else if( wrong_num_args ){
        sqliteErrorMsg(pParse,"wrong number of arguments to function %.*s()",
             nId, zId);
        nErr++;
      }
      if( is_agg ){
        pExpr->op = TK_AGG_FUNCTION;
        if( pIsAgg ) *pIsAgg = 1;
      }
      for(i=0; nErr==0 && i<n; i++){
        nErr = sqliteExprCheck(pParse, pExpr->pList->a[i].pExpr,
                               allowAgg && !is_agg, pIsAgg);
      }
      if( pDef==0 ){
        /* Already reported an error */
      }else if( pDef->dataType>=0 ){
        if( pDef->dataType<n ){
          pExpr->dataType = 
             sqliteExprType(pExpr->pList->a[pDef->dataType].pExpr);
        }else{
          pExpr->dataType = SQLITE_SO_NUM;
        }
      }else if( pDef->dataType==SQLITE_ARGS ){
        pDef->dataType = SQLITE_SO_TEXT;
        for(i=0; i<n; i++){
          if( sqliteExprType(pExpr->pList->a[i].pExpr)==SQLITE_SO_NUM ){
            pExpr->dataType = SQLITE_SO_NUM;
            break;
          }
        }
      }else if( pDef->dataType==SQLITE_NUMERIC ){
        pExpr->dataType = SQLITE_SO_NUM;
      }else{
        pExpr->dataType = SQLITE_SO_TEXT;
      }
    }
    default: {
      if( pExpr->pLeft ){
        nErr = sqliteExprCheck(pParse, pExpr->pLeft, allowAgg, pIsAgg);
      }
      if( nErr==0 && pExpr->pRight ){
        nErr = sqliteExprCheck(pParse, pExpr->pRight, allowAgg, pIsAgg);
      }
      if( nErr==0 && pExpr->pList ){
        int n = pExpr->pList->nExpr;
        int i;
        for(i=0; nErr==0 && i<n; i++){
          Expr *pE2 = pExpr->pList->a[i].pExpr;
          nErr = sqliteExprCheck(pParse, pE2, allowAgg, pIsAgg);
        }
      }
      break;
    }
  }
  return nErr;
}
示例#21
0
bool hasFunction(Aurora::GameID game, size_t n) {
	return !getFunctionName(game, n).empty();
}
示例#22
0
/*
** Generate code into the current Vdbe to evaluate the given
** expression and leave the result on the top of stack.
*/
void sqliteExprCode(Parse *pParse, Expr *pExpr){
  Vdbe *v = pParse->pVdbe;
  int op;
  if( v==0 || pExpr==0 ) return;
  switch( pExpr->op ){
    case TK_PLUS:     op = OP_Add;      break;
    case TK_MINUS:    op = OP_Subtract; break;
    case TK_STAR:     op = OP_Multiply; break;
    case TK_SLASH:    op = OP_Divide;   break;
    case TK_AND:      op = OP_And;      break;
    case TK_OR:       op = OP_Or;       break;
    case TK_LT:       op = OP_Lt;       break;
    case TK_LE:       op = OP_Le;       break;
    case TK_GT:       op = OP_Gt;       break;
    case TK_GE:       op = OP_Ge;       break;
    case TK_NE:       op = OP_Ne;       break;
    case TK_EQ:       op = OP_Eq;       break;
    case TK_ISNULL:   op = OP_IsNull;   break;
    case TK_NOTNULL:  op = OP_NotNull;  break;
    case TK_NOT:      op = OP_Not;      break;
    case TK_UMINUS:   op = OP_Negative; break;
    case TK_BITAND:   op = OP_BitAnd;   break;
    case TK_BITOR:    op = OP_BitOr;    break;
    case TK_BITNOT:   op = OP_BitNot;   break;
    case TK_LSHIFT:   op = OP_ShiftLeft;  break;
    case TK_RSHIFT:   op = OP_ShiftRight; break;
    case TK_REM:      op = OP_Remainder;  break;
    default: break;
  }
  switch( pExpr->op ){
    case TK_COLUMN: {
      if( pParse->useAgg ){
        sqliteVdbeAddOp(v, OP_AggGet, 0, pExpr->iAgg);
      }else if( pExpr->iColumn>=0 ){
        sqliteVdbeAddOp(v, OP_Column, pExpr->iTable, pExpr->iColumn);
      }else{
        sqliteVdbeAddOp(v, OP_Recno, pExpr->iTable, 0);
      }
      break;
    }
    case TK_STRING:
    case TK_FLOAT:
    case TK_INTEGER: {
      if( pExpr->op==TK_INTEGER && sqliteFitsIn32Bits(pExpr->token.z) ){
        sqliteVdbeAddOp(v, OP_Integer, atoi(pExpr->token.z), 0);
      }else{
        sqliteVdbeAddOp(v, OP_String, 0, 0);
      }
      assert( pExpr->token.z );
      sqliteVdbeChangeP3(v, -1, pExpr->token.z, pExpr->token.n);
      sqliteVdbeDequoteP3(v, -1);
      break;
    }
    case TK_NULL: {
      sqliteVdbeAddOp(v, OP_String, 0, 0);
      break;
    }
    case TK_VARIABLE: {
      sqliteVdbeAddOp(v, OP_Variable, pExpr->iTable, 0);
      break;
    }
    case TK_LT:
    case TK_LE:
    case TK_GT:
    case TK_GE:
    case TK_NE:
    case TK_EQ: {
      if( pParse->db->file_format>=4 && sqliteExprType(pExpr)==SQLITE_SO_TEXT ){
        op += 6;  /* Convert numeric opcodes to text opcodes */
      }
      /* Fall through into the next case */
    }
    case TK_AND:
    case TK_OR:
    case TK_PLUS:
    case TK_STAR:
    case TK_MINUS:
    case TK_REM:
    case TK_BITAND:
    case TK_BITOR:
    case TK_SLASH: {
      sqliteExprCode(pParse, pExpr->pLeft);
      sqliteExprCode(pParse, pExpr->pRight);
      sqliteVdbeAddOp(v, op, 0, 0);
      break;
    }
    case TK_LSHIFT:
    case TK_RSHIFT: {
      sqliteExprCode(pParse, pExpr->pRight);
      sqliteExprCode(pParse, pExpr->pLeft);
      sqliteVdbeAddOp(v, op, 0, 0);
      break;
    }
    case TK_CONCAT: {
      sqliteExprCode(pParse, pExpr->pLeft);
      sqliteExprCode(pParse, pExpr->pRight);
      sqliteVdbeAddOp(v, OP_Concat, 2, 0);
      break;
    }
    case TK_UMINUS: {
      assert( pExpr->pLeft );
      if( pExpr->pLeft->op==TK_FLOAT || pExpr->pLeft->op==TK_INTEGER ){
        Token *p = &pExpr->pLeft->token;
        char *z = sqliteMalloc( p->n + 2 );
        sprintf(z, "-%.*s", p->n, p->z);
        if( pExpr->pLeft->op==TK_INTEGER && sqliteFitsIn32Bits(z) ){
          sqliteVdbeAddOp(v, OP_Integer, atoi(z), 0);
        }else{
          sqliteVdbeAddOp(v, OP_String, 0, 0);
        }
        sqliteVdbeChangeP3(v, -1, z, p->n+1);
        sqliteFree(z);
        break;
      }
      /* Fall through into TK_NOT */
    }
    case TK_BITNOT:
    case TK_NOT: {
      sqliteExprCode(pParse, pExpr->pLeft);
      sqliteVdbeAddOp(v, op, 0, 0);
      break;
    }
    case TK_ISNULL:
    case TK_NOTNULL: {
      int dest;
      sqliteVdbeAddOp(v, OP_Integer, 1, 0);
      sqliteExprCode(pParse, pExpr->pLeft);
      dest = sqliteVdbeCurrentAddr(v) + 2;
      sqliteVdbeAddOp(v, op, 1, dest);
      sqliteVdbeAddOp(v, OP_AddImm, -1, 0);
      break;
    }
    case TK_AGG_FUNCTION: {
      sqliteVdbeAddOp(v, OP_AggGet, 0, pExpr->iAgg);
      break;
    }
    case TK_GLOB:
    case TK_LIKE:
    case TK_FUNCTION: {
      ExprList *pList = pExpr->pList;
      int nExpr = pList ? pList->nExpr : 0;
      FuncDef *pDef;
      int nId;
      const char *zId;
      getFunctionName(pExpr, &zId, &nId);
      pDef = sqliteFindFunction(pParse->db, zId, nId, nExpr, 0);
      assert( pDef!=0 );
      nExpr = sqliteExprCodeExprList(pParse, pList, pDef->includeTypes);
      sqliteVdbeOp3(v, OP_Function, nExpr, 0, (char*)pDef, P3_POINTER);
      break;
    }
    case TK_SELECT: {
      sqliteVdbeAddOp(v, OP_MemLoad, pExpr->iColumn, 0);
      break;
    }
    case TK_IN: {
      int addr;
      sqliteVdbeAddOp(v, OP_Integer, 1, 0);
      sqliteExprCode(pParse, pExpr->pLeft);
      addr = sqliteVdbeCurrentAddr(v);
      sqliteVdbeAddOp(v, OP_NotNull, -1, addr+4);
      sqliteVdbeAddOp(v, OP_Pop, 1, 0);
      sqliteVdbeAddOp(v, OP_String, 0, 0);
      sqliteVdbeAddOp(v, OP_Goto, 0, addr+6);
      if( pExpr->pSelect ){
        sqliteVdbeAddOp(v, OP_Found, pExpr->iTable, addr+6);
      }else{
        sqliteVdbeAddOp(v, OP_SetFound, pExpr->iTable, addr+6);
      }
      sqliteVdbeAddOp(v, OP_AddImm, -1, 0);
      break;
    }
    case TK_BETWEEN: {
      sqliteExprCode(pParse, pExpr->pLeft);
      sqliteVdbeAddOp(v, OP_Dup, 0, 0);
      sqliteExprCode(pParse, pExpr->pList->a[0].pExpr);
      sqliteVdbeAddOp(v, OP_Ge, 0, 0);
      sqliteVdbeAddOp(v, OP_Pull, 1, 0);
      sqliteExprCode(pParse, pExpr->pList->a[1].pExpr);
      sqliteVdbeAddOp(v, OP_Le, 0, 0);
      sqliteVdbeAddOp(v, OP_And, 0, 0);
      break;
    }
    case TK_UPLUS:
    case TK_AS: {
      sqliteExprCode(pParse, pExpr->pLeft);
      break;
    }
    case TK_CASE: {
      int expr_end_label;
      int jumpInst;
      int addr;
      int nExpr;
      int i;

      assert(pExpr->pList);
      assert((pExpr->pList->nExpr % 2) == 0);
      assert(pExpr->pList->nExpr > 0);
      nExpr = pExpr->pList->nExpr;
      expr_end_label = sqliteVdbeMakeLabel(v);
      if( pExpr->pLeft ){
        sqliteExprCode(pParse, pExpr->pLeft);
      }
      for(i=0; i<nExpr; i=i+2){
        sqliteExprCode(pParse, pExpr->pList->a[i].pExpr);
        if( pExpr->pLeft ){
          sqliteVdbeAddOp(v, OP_Dup, 1, 1);
          jumpInst = sqliteVdbeAddOp(v, OP_Ne, 1, 0);
          sqliteVdbeAddOp(v, OP_Pop, 1, 0);
        }else{
          jumpInst = sqliteVdbeAddOp(v, OP_IfNot, 1, 0);
        }
        sqliteExprCode(pParse, pExpr->pList->a[i+1].pExpr);
        sqliteVdbeAddOp(v, OP_Goto, 0, expr_end_label);
        addr = sqliteVdbeCurrentAddr(v);
        sqliteVdbeChangeP2(v, jumpInst, addr);
      }
      if( pExpr->pLeft ){
        sqliteVdbeAddOp(v, OP_Pop, 1, 0);
      }
      if( pExpr->pRight ){
        sqliteExprCode(pParse, pExpr->pRight);
      }else{
        sqliteVdbeAddOp(v, OP_String, 0, 0);
      }
      sqliteVdbeResolveLabel(v, expr_end_label);
      break;
    }
    case TK_RAISE: {
      if( !pParse->trigStack ){
        sqliteErrorMsg(pParse,
                       "RAISE() may only be used within a trigger-program");
        pParse->nErr++;
	return;
      }
      if( pExpr->iColumn == OE_Rollback ||
	  pExpr->iColumn == OE_Abort ||
	  pExpr->iColumn == OE_Fail ){
	  sqliteVdbeOp3(v, OP_Halt, SQLITE_CONSTRAINT, pExpr->iColumn,
                           pExpr->token.z, pExpr->token.n);
	  sqliteVdbeDequoteP3(v, -1);
      } else {
	  assert( pExpr->iColumn == OE_Ignore );
	  sqliteVdbeOp3(v, OP_Goto, 0, pParse->trigStack->ignoreJump,
                           "(IGNORE jump)", 0);
      }
    }
    break;
  }
}