List of usage examples for org.objectweb.asm Opcodes INVOKESTATIC
int INVOKESTATIC
To view the source code for org.objectweb.asm Opcodes INVOKESTATIC.
Click Source Link
From source file:jpcsp.Allegrex.compiler.CompilerContext.java
License:Open Source License
/** * Generate the required Java code to load one parameter for * the syscall function from the CPU registers. * * The following code is generated based on the parameter type: * Processor: parameterValue = RuntimeContext.processor * int: parameterValue = cpu.gpr[paramIndex++] * float: parameterValue = cpu.fpr[paramFloatIndex++] * long: parameterValue = (cpu.gpr[paramIndex++] & 0xFFFFFFFFL) + ((long) cpu.gpr[paramIndex++]) << 32) * boolean: parameterValue = cpu.gpr[paramIndex++] * TPointer,//from w w w . j a va 2 s . co m * TPointer8, * TPointer16, * TPointer32, * TPointer64, * TErrorPointer32: * if (checkMemoryAccess()) { * if (canBeNullParam && address == 0) { * goto addressGood; * } * if (RuntimeContext.checkMemoryPointer(address)) { * goto addressGood; * } * cpu.gpr[_v0] = SceKernelErrors.ERROR_INVALID_POINTER; * pop all the parameters already prepared on the stack; * goto afterSyscall; * addressGood: * } * <parameterType> pointer = new <parameterType>(address); * if (parameterType == TErrorPointer32.class) { * parameterReader.setHasErrorPointer(true); * localVar[LOCAL_ERROR_POINTER] = pointer; * } * parameterValue = pointer * HLEUidClass defined in annotation: * <parameterType> uidObject = HLEUidObjectMapping.getObject("<parameterType>", uid); * if (uidObject == null) { * cpu.gpr[_v0] = errorValueOnNotFound; * pop all the parameters already prepared on the stack; * goto afterSyscall; * } * parameterValue = uidObject * * And then common for all the types: * try { * parameterValue = <module>.<methodToCheck>(parameterValue); * } catch (SceKernelErrorException e) { * goto catchSceKernelErrorException; * } * push parameterValue on stack * * @param parameterReader the current parameter state * @param func the syscall function * @param parameterType the type of the parameter * @param afterSyscallLabel the Label pointing after the call to the syscall function * @param catchSceKernelErrorException the Label pointing to the SceKernelErrorException catch handler */ private void loadParameter(CompilerParameterReader parameterReader, HLEModuleFunction func, Class<?> parameterType, Annotation[] parameterAnnotations, Label afterSyscallLabel, Label catchSceKernelErrorException) { if (parameterType == Processor.class) { loadProcessor(); parameterReader.incrementCurrentStackSize(); } else if (parameterType == CpuState.class) { loadCpu(); parameterReader.incrementCurrentStackSize(); } else if (parameterType == int.class) { parameterReader.loadNextInt(); parameterReader.incrementCurrentStackSize(); } else if (parameterType == float.class) { parameterReader.loadNextFloat(); parameterReader.incrementCurrentStackSize(); } else if (parameterType == long.class) { parameterReader.loadNextLong(); parameterReader.incrementCurrentStackSize(2); } else if (parameterType == boolean.class) { parameterReader.loadNextInt(); parameterReader.incrementCurrentStackSize(); } else if (parameterType == String.class) { parameterReader.loadNextInt(); int maxLength = 16 * 1024; for (Annotation parameterAnnotation : parameterAnnotations) { if (parameterAnnotation instanceof StringInfo) { StringInfo stringInfo = ((StringInfo) parameterAnnotation); maxLength = stringInfo.maxLength(); break; } } loadImm(maxLength); mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "readStringNZ", "(II)" + Type.getDescriptor(String.class)); parameterReader.incrementCurrentStackSize(); } else if (parameterType == PspString.class) { parameterReader.loadNextInt(); int maxLength = 16 * 1024; boolean canBeNull = false; for (Annotation parameterAnnotation : parameterAnnotations) { if (parameterAnnotation instanceof StringInfo) { StringInfo stringInfo = ((StringInfo) parameterAnnotation); maxLength = stringInfo.maxLength(); } if (parameterAnnotation instanceof CanBeNull) { canBeNull = true; } } loadImm(maxLength); loadImm(canBeNull); mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "readPspStringNZ", "(IIZ)" + Type.getDescriptor(PspString.class)); parameterReader.incrementCurrentStackSize(); } else if (parameterType == TPointer.class || parameterType == TPointer8.class || parameterType == TPointer16.class || parameterType == TPointer32.class || parameterType == TPointer64.class || parameterType == TErrorPointer32.class) { // if (checkMemoryAccess()) { // if (canBeNullParam && address == 0) { // goto addressGood; // } // if (RuntimeContext.checkMemoryPointer(address)) { // goto addressGood; // } // cpu.gpr[_v0] = SceKernelErrors.ERROR_INVALID_POINTER; // pop all the parameters already prepared on the stack; // goto afterSyscall; // addressGood: // } // <parameterType> pointer = new <parameterType>(address); // if (parameterType == TErrorPointer32.class) { // parameterReader.setHasErrorPointer(true); // localVar[LOCAL_ERROR_POINTER] = pointer; // } mv.visitTypeInsn(Opcodes.NEW, Type.getInternalName(parameterType)); mv.visitInsn(Opcodes.DUP); loadMemory(); parameterReader.loadNextInt(); boolean canBeNull = false; for (Annotation parameterAnnotation : parameterAnnotations) { if (parameterAnnotation instanceof CanBeNull) { canBeNull = true; break; } } if (checkMemoryAccess() && afterSyscallLabel != null) { Label addressGood = new Label(); if (canBeNull) { mv.visitInsn(Opcodes.DUP); mv.visitJumpInsn(Opcodes.IFEQ, addressGood); } mv.visitInsn(Opcodes.DUP); mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "checkMemoryPointer", "(I)Z"); mv.visitJumpInsn(Opcodes.IFNE, addressGood); storeRegister(_v0, SceKernelErrors.ERROR_INVALID_POINTER); parameterReader.popAllStack(4); mv.visitJumpInsn(Opcodes.GOTO, afterSyscallLabel); mv.visitLabel(addressGood); } if (parameterType == TPointer8.class || parameterType == TPointer16.class || parameterType == TPointer32.class || parameterType == TPointer64.class) { loadImm(canBeNull); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, Type.getInternalName(parameterType), "<init>", "(" + memoryDescriptor + "IZ)V"); } else { mv.visitMethodInsn(Opcodes.INVOKESPECIAL, Type.getInternalName(parameterType), "<init>", "(" + memoryDescriptor + "I)V"); } if (parameterType == TErrorPointer32.class) { parameterReader.setHasErrorPointer(true); mv.visitInsn(Opcodes.DUP); mv.visitVarInsn(Opcodes.ASTORE, LOCAL_ERROR_POINTER); } parameterReader.incrementCurrentStackSize(); } else if (pspAbstractMemoryMappedStructure.class.isAssignableFrom(parameterType)) { parameterReader.loadNextInt(); boolean canBeNull = false; for (Annotation parameterAnnotation : parameterAnnotations) { if (parameterAnnotation instanceof CanBeNull) { canBeNull = true; break; } } if (checkMemoryAccess() && afterSyscallLabel != null) { Label addressGood = new Label(); if (canBeNull) { mv.visitInsn(Opcodes.DUP); mv.visitJumpInsn(Opcodes.IFEQ, addressGood); } mv.visitInsn(Opcodes.DUP); mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "checkMemoryPointer", "(I)Z"); mv.visitJumpInsn(Opcodes.IFNE, addressGood); storeRegister(_v0, SceKernelErrors.ERROR_INVALID_POINTER); parameterReader.popAllStack(1); mv.visitJumpInsn(Opcodes.GOTO, afterSyscallLabel); mv.visitLabel(addressGood); } mv.visitTypeInsn(Opcodes.NEW, Type.getInternalName(parameterType)); mv.visitInsn(Opcodes.DUP); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, Type.getInternalName(parameterType), "<init>", "()V"); mv.visitInsn(Opcodes.DUP_X1); mv.visitInsn(Opcodes.SWAP); loadMemory(); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(parameterType), "read", "(" + memoryDescriptor + "I)V"); parameterReader.incrementCurrentStackSize(); } else { HLEUidClass hleUidClass = parameterType.getAnnotation(HLEUidClass.class); if (hleUidClass != null) { int errorValueOnNotFound = hleUidClass.errorValueOnNotFound(); // <parameterType> uidObject = HLEUidObjectMapping.getObject("<parameterType>", uid); // if (uidObject == null) { // cpu.gpr[_v0] = errorValueOnNotFound; // pop all the parameters already prepared on the stack; // goto afterSyscall; // } mv.visitLdcInsn(parameterType.getName()); // Load the UID parameterReader.loadNextInt(); // Load the UID Object mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(HLEUidObjectMapping.class), "getObject", "(" + Type.getDescriptor(String.class) + "I)" + Type.getDescriptor(Object.class)); if (afterSyscallLabel != null) { Label foundUid = new Label(); mv.visitInsn(Opcodes.DUP); mv.visitJumpInsn(Opcodes.IFNONNULL, foundUid); storeRegister(_v0, errorValueOnNotFound); parameterReader.popAllStack(1); mv.visitJumpInsn(Opcodes.GOTO, afterSyscallLabel); mv.visitLabel(foundUid); } mv.visitTypeInsn(Opcodes.CHECKCAST, Type.getInternalName(parameterType)); parameterReader.incrementCurrentStackSize(); } else { log.error(String.format("Unsupported sycall parameter type '%s'", parameterType.getName())); Emulator.PauseEmuWithStatus(Emulator.EMU_STATUS_UNIMPLEMENTED); } } Method methodToCheck = null; if (afterSyscallLabel != null) { for (Annotation parameterAnnotation : parameterAnnotations) { if (parameterAnnotation instanceof CheckArgument) { CheckArgument checkArgument = (CheckArgument) parameterAnnotation; try { methodToCheck = func.getHLEModule().getClass().getMethod(checkArgument.value(), parameterType); } catch (Exception e) { log.error(String.format("CheckArgument method '%s' not found in %s", checkArgument.value(), func.getModuleName()), e); } break; } } } if (methodToCheck != null) { // try { // parameterValue = <module>.<methodToCheck>(parameterValue); // } catch (SceKernelErrorException e) { // goto catchSceKernelErrorException; // } loadModule(func.getModuleName()); mv.visitInsn(Opcodes.SWAP); Label tryStart = new Label(); Label tryEnd = new Label(); mv.visitTryCatchBlock(tryStart, tryEnd, catchSceKernelErrorException, Type.getInternalName(SceKernelErrorException.class)); mv.visitLabel(tryStart); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(methodToCheck.getDeclaringClass()), methodToCheck.getName(), "(" + Type.getDescriptor(parameterType) + ")" + Type.getDescriptor(parameterType)); mv.visitLabel(tryEnd); } parameterReader.incrementCurrentParameterIndex(); }
From source file:jpcsp.Allegrex.compiler.CompilerContext.java
License:Open Source License
/** * Generate the required Java code to store the return value of * the syscall function into the CPU registers. * * The following code is generated depending on the return type: * void: -/* w ww . j av a2 s .c o m*/ * int: cpu.gpr[_v0] = intValue * boolean: cpu.gpr[_v0] = booleanValue * long: cpu.gpr[_v0] = (int) (longValue & 0xFFFFFFFFL) * cpu.gpr[_v1] = (int) (longValue >>> 32) * float: cpu.fpr[_f0] = floatValue * HLEUidClass: if (moduleMethodUidGenerator == "") { * cpu.gpr[_v0] = HLEUidObjectMapping.createUidForObject("<return type>", returnValue); * } else { * int uid = <module>.<moduleMethodUidGenerator>(); * cpu.gpr[_v0] = HLEUidObjectMapping.addObjectMap("<return type>", uid, returnValue); * } * * @param func the syscall function * @param returnType the type of the return value */ private void storeReturnValue(HLEModuleFunction func, Class<?> returnType) { if (returnType == void.class) { // Nothing to do } else if (returnType == int.class) { // cpu.gpr[_v0] = intValue storeRegister(_v0); } else if (returnType == boolean.class) { // cpu.gpr[_v0] = booleanValue storeRegister(_v0); } else if (returnType == long.class) { // cpu.gpr[_v0] = (int) (longValue & 0xFFFFFFFFL) // cpu.gpr[_v1] = (int) (longValue >>> 32) mv.visitInsn(Opcodes.DUP2); mv.visitLdcInsn(0xFFFFFFFFL); mv.visitInsn(Opcodes.LAND); mv.visitInsn(Opcodes.L2I); storeRegister(_v0); loadImm(32); mv.visitInsn(Opcodes.LSHR); mv.visitInsn(Opcodes.L2I); storeRegister(_v1); } else if (returnType == float.class) { // cpu.fpr[_f0] = floatValue storeFRegister(_f0); } else { HLEUidClass hleUidClass = returnType.getAnnotation(HLEUidClass.class); if (hleUidClass != null) { // if (moduleMethodUidGenerator == "") { // cpu.gpr[_v0] = HLEUidObjectMapping.createUidForObject("<return type>", returnValue); // } else { // int uid = <module>.<moduleMethodUidGenerator>(); // cpu.gpr[_v0] = HLEUidObjectMapping.addObjectMap("<return type>", uid, returnValue); // } if (hleUidClass.moduleMethodUidGenerator().length() <= 0) { // No UID generator method, use the default one mv.visitLdcInsn(returnType.getName()); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(HLEUidObjectMapping.class), "createUidForObject", "(" + Type.getDescriptor(String.class) + Type.getDescriptor(Object.class) + ")I"); storeRegister(_v0); } else { mv.visitLdcInsn(returnType.getName()); mv.visitInsn(Opcodes.SWAP); loadModule(func.getModuleName()); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(func.getHLEModuleMethod().getDeclaringClass()), hleUidClass.moduleMethodUidGenerator(), "()I"); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(HLEUidObjectMapping.class), "addObjectMap", "(" + Type.getDescriptor(String.class) + "I" + Type.getDescriptor(Object.class) + ")I"); storeRegister(_v0); } } else { log.error(String.format("Unsupported sycall return value type '%s'", returnType.getName())); } } }
From source file:jpcsp.Allegrex.compiler.CompilerContext.java
License:Open Source License
private void logSyscall(HLEModuleFunction func, String logPrefix, String logCheckFunction, String logFunction) { // Modules.getLogger(func.getModuleName()).warn("Unimplemented..."); loadModuleLoggger(func);/*from w w w . j av a2 s.c om*/ mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Logger.class), logCheckFunction, "()Z"); Label loggingDisabled = new Label(); mv.visitJumpInsn(Opcodes.IFEQ, loggingDisabled); loadModuleLoggger(func); StringBuilder formatString = new StringBuilder(); if (logPrefix != null) { formatString.append(logPrefix); } formatString.append(func.getFunctionName()); ParameterInfo[] parameters = new ClassAnalyzer().getParameters(func.getFunctionName(), func.getHLEModuleMethod().getDeclaringClass()); if (parameters != null) { // Log message: // String.format( // "Unimplemented <function name> // <parameterIntegerName>=0x%X, // <parameterBooleanName>=%b, // <parameterLongName>=0x%X, // <parameterFloatName>=%f, // <parameterOtherTypeName>=%s", // new Object[] { // new Integer(parameterValueInteger), // new Boolean(parameterValueBoolean), // new Long(parameterValueLong), // new Float(parameterValueFloat), // parameterValueOtherTypes // }) loadImm(parameters.length); mv.visitTypeInsn(Opcodes.ANEWARRAY, Type.getInternalName(Object.class)); CompilerParameterReader parameterReader = new CompilerParameterReader(this); Annotation[][] paramsAnotations = func.getHLEModuleMethod().getParameterAnnotations(); int objectArrayIndex = 0; for (int paramIndex = 0; paramIndex < parameters.length; paramIndex++) { ParameterInfo parameter = parameters[paramIndex]; Class<?> parameterType = parameter.type; CompilerTypeInformation typeInformation = compilerTypeManager .getCompilerTypeInformation(parameterType); mv.visitInsn(Opcodes.DUP); loadImm(objectArrayIndex); formatString.append(paramIndex > 0 ? ", " : " "); formatString.append(parameter.name); formatString.append("="); formatString.append(typeInformation.formatString); if (typeInformation.boxingTypeInternalName != null) { mv.visitTypeInsn(Opcodes.NEW, typeInformation.boxingTypeInternalName); mv.visitInsn(Opcodes.DUP); } loadParameter(parameterReader, func, parameterType, paramsAnotations[paramIndex], null, null); if (typeInformation.boxingTypeInternalName != null) { mv.visitMethodInsn(Opcodes.INVOKESPECIAL, typeInformation.boxingTypeInternalName, "<init>", typeInformation.boxingMethodDescriptor); } mv.visitInsn(Opcodes.AASTORE); objectArrayIndex++; } mv.visitLdcInsn(formatString.toString()); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(String.class), "format", "(" + Type.getDescriptor(String.class) + "[" + Type.getDescriptor(Object.class) + ")" + Type.getDescriptor(String.class)); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Logger.class), logFunction, "(" + Type.getDescriptor(Object.class) + ")V"); parameterReader = new CompilerParameterReader(this); for (int paramIndex = 0; paramIndex < parameters.length; paramIndex++) { ParameterInfo parameter = parameters[paramIndex]; Class<?> parameterType = parameter.type; LengthInfo lengthInfo = BufferInfo.defaultLengthInfo; int length = BufferInfo.defaultLength; Usage usage = BufferInfo.defaultUsage; for (Annotation parameterAnnotation : paramsAnotations[paramIndex]) { if (parameterAnnotation instanceof BufferInfo) { BufferInfo bufferInfo = (BufferInfo) parameterAnnotation; lengthInfo = bufferInfo.lengthInfo(); length = bufferInfo.length(); usage = bufferInfo.usage(); } } boolean parameterRead = false; if ((usage == Usage.in || usage == Usage.inout) && (lengthInfo != LengthInfo.unknown || parameterType == TPointer16.class || parameterType == TPointer32.class || parameterType == TPointer64.class)) { loadModuleLoggger(func); loadImm(1); mv.visitTypeInsn(Opcodes.ANEWARRAY, Type.getInternalName(Object.class)); mv.visitInsn(Opcodes.DUP); loadImm(0); Label done = new Label(); Label addressNull = new Label(); parameterReader.loadNextInt(); parameterRead = true; mv.visitInsn(Opcodes.DUP); mv.visitJumpInsn(Opcodes.IFEQ, addressNull); String format = String.format("%s[%s]:%%s", parameter.name, usage); boolean useMemoryDump = true; switch (lengthInfo) { case fixedLength: loadImm(length); break; case nextNextParameter: parameterReader.skipNextInt(); paramIndex++; parameterReader.loadNextInt(); paramIndex++; break; case nextParameter: parameterReader.loadNextInt(); paramIndex++; break; case previousParameter: // Go back to the address parameter parameterReader.rewindPreviousInt(); // Go back to the previous parameter parameterReader.rewindPreviousInt(); // Load the length from the previous parameter parameterReader.loadNextInt(); // Skip again the address parameter // to come back to the above situation parameterReader.skipNextInt(); break; case variableLength: mv.visitInsn(Opcodes.DUP); loadMemory(); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, memoryInternalName, "read32", "(I)I"); break; case unknown: useMemoryDump = false; format = String.format("%s[%s]: 0x%%X", parameter.name, usage); loadMemory(); mv.visitInsn(Opcodes.SWAP); if (parameterType == TPointer64.class) { mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, memoryInternalName, "read64", "(I)J"); mv.visitTypeInsn(Opcodes.NEW, Type.getInternalName(Long.class)); mv.visitInsn(Opcodes.DUP); mv.visitInsn(Opcodes.DUP2_X2); mv.visitInsn(Opcodes.POP2); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, Type.getInternalName(Long.class), "<init>", "(J)V"); } else if (parameterType == TPointer16.class) { mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, memoryInternalName, "read16", "(I)I"); mv.visitTypeInsn(Opcodes.NEW, Type.getInternalName(Integer.class)); mv.visitInsn(Opcodes.DUP_X1); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, Type.getInternalName(Integer.class), "<init>", "(I)V"); } else { mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, memoryInternalName, "read32", "(I)I"); mv.visitTypeInsn(Opcodes.NEW, Type.getInternalName(Integer.class)); mv.visitInsn(Opcodes.DUP_X1); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, Type.getInternalName(Integer.class), "<init>", "(I)V"); } break; default: log.error(String.format("Unimplemented lengthInfo=%s", lengthInfo)); break; } if (useMemoryDump) { mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(Utilities.class), "getMemoryDump", "(II)" + Type.getDescriptor(String.class)); } mv.visitInsn(Opcodes.AASTORE); mv.visitLdcInsn(format); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(String.class), "format", "(" + Type.getDescriptor(String.class) + "[" + Type.getDescriptor(Object.class) + ")" + Type.getDescriptor(String.class)); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Logger.class), logFunction, "(" + Type.getDescriptor(Object.class) + ")V"); mv.visitJumpInsn(Opcodes.GOTO, done); mv.visitLabel(addressNull); mv.visitInsn(Opcodes.POP); mv.visitInsn(Opcodes.POP2); mv.visitInsn(Opcodes.POP2); mv.visitLabel(done); } if (!parameterRead) { if (parameterType == long.class) { parameterReader.skipNextLong(); } else if (parameterType == float.class) { parameterReader.skipNextFloat(); } else { parameterReader.skipNextInt(); } } } } else { mv.visitLdcInsn(formatString.toString()); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Logger.class), logFunction, "(" + Type.getDescriptor(Object.class) + ")V"); } mv.visitLabel(loggingDisabled); }
From source file:jpcsp.Allegrex.compiler.CompilerContext.java
License:Open Source License
private void logSyscallEnd(HLEModuleFunction func, boolean isErrorCode) { String loggingLevel = getLoggingLevel(func); if (loggingLevel == null) { return;/*from w ww .j a v a 2 s . c o m*/ } String logCheckFunction = getLogCheckFunction(loggingLevel); // if (Modules.getLogger(func.getModuleName()).isDebugEnabled()) { // Modules.getLogger(func.getModuleName()).debug(String.format("<function name> returning 0x%X", new Object[1] { new Integer(returnValue) })); // } loadModuleLoggger(func); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Logger.class), logCheckFunction, "()Z"); Label notDebug = new Label(); mv.visitJumpInsn(Opcodes.IFEQ, notDebug); boolean isReturningVoid = func.getHLEModuleMethod().getReturnType() == void.class; mv.visitInsn(Opcodes.DUP); mv.visitTypeInsn(Opcodes.NEW, Type.getInternalName(Integer.class)); mv.visitInsn(Opcodes.DUP_X1); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, Type.getInternalName(Integer.class), "<init>", "(I)V"); loadImm(1); mv.visitTypeInsn(Opcodes.ANEWARRAY, Type.getInternalName(Object.class)); mv.visitInsn(Opcodes.DUP_X1); mv.visitInsn(Opcodes.SWAP); loadImm(0); mv.visitInsn(Opcodes.SWAP); mv.visitInsn(Opcodes.AASTORE); String prefix = func.isUnimplemented() && !codeBlock.isHLEFunction() ? "Unimplemented " : ""; mv.visitLdcInsn(String.format("%s%s returning %s%s", prefix, func.getFunctionName(), isErrorCode ? "errorCode " : "", isReturningVoid ? "void" : "0x%X")); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(String.class), "format", "(" + Type.getDescriptor(String.class) + "[" + Type.getDescriptor(Object.class) + ")" + Type.getDescriptor(String.class)); loadModuleLoggger(func); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Logger.class), loggingLevel, "(" + Type.getDescriptor(Object.class) + ")V"); if (!isErrorCode) { ParameterInfo[] parameters = new ClassAnalyzer().getParameters(func.getFunctionName(), func.getHLEModuleMethod().getDeclaringClass()); if (parameters != null) { CompilerParameterReader parameterReader; if (parametersSavedToLocals) { parameterReader = new CompilerLocalVarParameterReader(this, LOCAL_FIRST_SAVED_PARAMETER); } else { parameterReader = new CompilerParameterReader(this); } Annotation[][] paramsAnotations = func.getHLEModuleMethod().getParameterAnnotations(); for (int paramIndex = 0; paramIndex < parameters.length; paramIndex++) { ParameterInfo parameter = parameters[paramIndex]; Class<?> parameterType = parameter.type; LengthInfo lengthInfo = BufferInfo.defaultLengthInfo; int length = BufferInfo.defaultLength; Usage usage = BufferInfo.defaultUsage; boolean debugMemory = false; for (Annotation parameterAnnotation : paramsAnotations[paramIndex]) { if (parameterAnnotation instanceof BufferInfo) { BufferInfo bufferInfo = (BufferInfo) parameterAnnotation; lengthInfo = bufferInfo.lengthInfo(); length = bufferInfo.length(); usage = bufferInfo.usage(); } else if (parameterAnnotation instanceof DebugMemory) { debugMemory = true; } } boolean parameterRead = false; if ((usage == Usage.out || usage == Usage.inout) && (lengthInfo != LengthInfo.unknown || parameterType == TPointer16.class || parameterType == TPointer32.class || parameterType == TPointer64.class)) { loadModuleLoggger(func); loadImm(1); mv.visitTypeInsn(Opcodes.ANEWARRAY, Type.getInternalName(Object.class)); mv.visitInsn(Opcodes.DUP); loadImm(0); Label done = new Label(); Label addressNull = new Label(); parameterReader.loadNextInt(); parameterRead = true; mv.visitInsn(Opcodes.DUP); mv.visitJumpInsn(Opcodes.IFEQ, addressNull); String format = String.format("%s[%s]:%%s", parameter.name, usage); boolean useMemoryDump = true; switch (lengthInfo) { case fixedLength: loadImm(length); break; case nextNextParameter: parameterReader.skipNextInt(); paramIndex++; parameterReader.loadNextInt(); paramIndex++; break; case nextParameter: parameterReader.loadNextInt(); paramIndex++; break; case previousParameter: // Go back to the address parameter parameterReader.rewindPreviousInt(); // Go back to the previous parameter parameterReader.rewindPreviousInt(); // Load the length from the previous parameter parameterReader.loadNextInt(); // Skip again the address parameter // to come back to the above situation parameterReader.skipNextInt(); break; case variableLength: mv.visitInsn(Opcodes.DUP); loadMemory(); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, memoryInternalName, "read32", "(I)I"); break; case returnValue: loadRegister(_v0); break; case unknown: useMemoryDump = false; format = String.format("%s[%s]: 0x%%X", parameter.name, usage); loadMemory(); mv.visitInsn(Opcodes.SWAP); if (parameterType == TPointer64.class) { if (debugMemory) { mv.visitInsn(Opcodes.DUP); loadImm(8); mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "debugMemory", "(II)V"); } mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, memoryInternalName, "read64", "(I)J"); mv.visitTypeInsn(Opcodes.NEW, Type.getInternalName(Long.class)); mv.visitInsn(Opcodes.DUP); mv.visitInsn(Opcodes.DUP2_X2); mv.visitInsn(Opcodes.POP2); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, Type.getInternalName(Long.class), "<init>", "(J)V"); } else if (parameterType == TPointer16.class) { if (debugMemory) { mv.visitInsn(Opcodes.DUP); loadImm(2); mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "debugMemory", "(II)V"); } mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, memoryInternalName, "read16", "(I)I"); mv.visitTypeInsn(Opcodes.NEW, Type.getInternalName(Integer.class)); mv.visitInsn(Opcodes.DUP_X1); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, Type.getInternalName(Integer.class), "<init>", "(I)V"); } else { if (debugMemory) { mv.visitInsn(Opcodes.DUP); loadImm(4); mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "debugMemory", "(II)V"); } mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, memoryInternalName, "read32", "(I)I"); mv.visitTypeInsn(Opcodes.NEW, Type.getInternalName(Integer.class)); mv.visitInsn(Opcodes.DUP_X1); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKESPECIAL, Type.getInternalName(Integer.class), "<init>", "(I)V"); } break; default: log.error(String.format("Unimplemented lengthInfo=%s", lengthInfo)); break; } if (useMemoryDump) { if (debugMemory) { mv.visitInsn(Opcodes.DUP2); mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "debugMemory", "(II)V"); } mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(Utilities.class), "getMemoryDump", "(II)" + Type.getDescriptor(String.class)); } mv.visitInsn(Opcodes.AASTORE); mv.visitLdcInsn(format); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(String.class), "format", "(" + Type.getDescriptor(String.class) + "[" + Type.getDescriptor(Object.class) + ")" + Type.getDescriptor(String.class)); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Logger.class), loggingLevel, "(" + Type.getDescriptor(Object.class) + ")V"); mv.visitJumpInsn(Opcodes.GOTO, done); mv.visitLabel(addressNull); mv.visitInsn(Opcodes.POP); mv.visitInsn(Opcodes.POP2); mv.visitInsn(Opcodes.POP2); mv.visitLabel(done); } if (!parameterRead) { if (parameterType == long.class) { parameterReader.skipNextLong(); } else if (parameterType == float.class) { parameterReader.skipNextFloat(); } else { parameterReader.skipNextInt(); } } } } } mv.visitLabel(notDebug); }
From source file:jpcsp.Allegrex.compiler.CompilerContext.java
License:Open Source License
/** * Generate the required Java code to call a syscall function. * The code generated must match the Java behavior implemented in * jpcsp.HLE.modules.HLEModuleFunctionReflection * * The following code is generated://from ww w. j a v a 2 s. c o m * if (func.getFirmwareVersion() <= RuntimeContext.firmwareVersion) { * if (!fastSyscall) { * RuntimeContext.preSyscall(); * } * if (func.checkInsideInterrupt()) { * if (IntrManager.getInstance.isInsideInterrupt()) { * cpu.gpr[_v0] = SceKernelErrors.ERROR_KERNEL_CANNOT_BE_CALLED_FROM_INTERRUPT; * goto afterSyscall; * } * } * if (func.checkDispatchThreadEnabled()) { * if (!Modules.ThreadManForUserModule.isDispatchThreadEnabled()) { * cpu.gpr[_v0] = SceKernelErrors.ERROR_KERNEL_WAIT_CAN_NOT_WAIT; * goto afterSyscall; * } * } * if (func.isUnimplemented()) { * Modules.getLogger(func.getModuleName()).warn("Unimplemented <function name> parameterName1=parameterValue1, parameterName2=parameterValue2, ..."); * } * foreach parameter { * loadParameter(parameter); * } * try { * returnValue = <module name>.<function name>(...parameters...); * storeReturnValue(); * if (parameterReader.hasErrorPointer()) { * errorPointer.setValue(0); * } * } catch (SceKernelErrorException e) { * errorCode = e.errorCode; * if (Modules.getLogger(func.getModuleName()).isDebugEnabled()) { * Modules.getLogger(func.getModuleName()).debug(String.format("<function name> return errorCode 0x%08X", errorCode)); * } * if (parameterReader.hasErrorPointer()) { * errorPointer.setValue(errorCode); * cpu.gpr[_v0] = 0; * } else { * cpu.gpr[_v0] = errorCode; * } * reload cpu.gpr[_ra]; // an exception is always clearing the whole stack * } * afterSyscall: * if (fastSyscall) { * RuntimeContext.postSyscallFast(); * } else { * RuntimeContext.postSyscall(); * } * } else { * Modules.getLogger(func.getModuleName()).warn("<function name> is not supported in firmware version <firmwareVersion>, it requires at least firmware version <function firmwareVersion>"); * cpu.gpr[_v0] = -1; * } * * @param func the syscall function * @param fastSyscall true if this is a fast syscall (i.e. without context switching) * false if not (i.e. a syscall where context switching could happen) */ private void visitSyscall(HLEModuleFunction func, boolean fastSyscall) { // The compilation of a syscall requires more stack size than usual maxStackSize = SYSCALL_MAX_STACK_SIZE; boolean needFirmwareVersionCheck = true; if (func.getFirmwareVersion() >= 999) { // Dummy version number meaning valid for all versions needFirmwareVersionCheck = false; } else if (isCodeInstructionInKernelMemory()) { // When compiling code in the kernel memory space, do not perform any version check. // This is used by overwritten HLE functions. needFirmwareVersionCheck = false; } else { // When compiling code loaded from flash0, do not perform any version check. // This is used by overwritten HLE functions. SceModule module = Managers.modules.getModuleByAddress(codeInstruction.getAddress()); if (module != null && module.pspfilename != null && module.pspfilename.startsWith("flash0:")) { if (log.isDebugEnabled()) { log.debug(String.format("syscall from a flash0 module(%s, '%s'), no firmware version check", module, module.pspfilename)); } needFirmwareVersionCheck = false; } } Label unsupportedVersionLabel = null; if (needFirmwareVersionCheck) { unsupportedVersionLabel = new Label(); loadImm(func.getFirmwareVersion()); mv.visitFieldInsn(Opcodes.GETSTATIC, runtimeContextInternalName, "firmwareVersion", "I"); mv.visitJumpInsn(Opcodes.IF_ICMPGT, unsupportedVersionLabel); } // Save the syscall parameter to locals for debugging if (!fastSyscall) { saveParametersToLocals(); } if (!fastSyscall) { mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "preSyscall", "()V"); } Label afterSyscallLabel = new Label(); if (func.checkInsideInterrupt()) { // if (IntrManager.getInstance().isInsideInterrupt()) { // if (Modules.getLogger(func.getModuleName()).isDebugEnabled()) { // Modules.getLogger(func.getModuleName()).debug("<function name> return errorCode 0x80020064 (ERROR_KERNEL_CANNOT_BE_CALLED_FROM_INTERRUPT)"); // } // cpu.gpr[_v0] = SceKernelErrors.ERROR_KERNEL_CANNOT_BE_CALLED_FROM_INTERRUPT; // goto afterSyscall // } mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(IntrManager.class), "getInstance", "()" + Type.getDescriptor(IntrManager.class)); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(IntrManager.class), "isInsideInterrupt", "()Z"); Label notInsideInterrupt = new Label(); mv.visitJumpInsn(Opcodes.IFEQ, notInsideInterrupt); loadModuleLoggger(func); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Logger.class), "isDebugEnabled", "()Z"); Label notDebug = new Label(); mv.visitJumpInsn(Opcodes.IFEQ, notDebug); loadModuleLoggger(func); mv.visitLdcInsn( String.format("%s returning errorCode 0x%08X (ERROR_KERNEL_CANNOT_BE_CALLED_FROM_INTERRUPT)", func.getFunctionName(), SceKernelErrors.ERROR_KERNEL_CANNOT_BE_CALLED_FROM_INTERRUPT)); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Logger.class), "debug", "(" + Type.getDescriptor(Object.class) + ")V"); mv.visitLabel(notDebug); storeRegister(_v0, SceKernelErrors.ERROR_KERNEL_CANNOT_BE_CALLED_FROM_INTERRUPT); mv.visitJumpInsn(Opcodes.GOTO, afterSyscallLabel); mv.visitLabel(notInsideInterrupt); } if (func.checkDispatchThreadEnabled()) { // if (!Modules.ThreadManForUserModule.isDispatchThreadEnabled() || !Interrupts.isInterruptsEnabled()) { // if (Modules.getLogger(func.getModuleName()).isDebugEnabled()) { // Modules.getLogger(func.getModuleName()).debug("<function name> return errorCode 0x800201A7 (ERROR_KERNEL_WAIT_CAN_NOT_WAIT)"); // } // cpu.gpr[_v0] = SceKernelErrors.ERROR_KERNEL_WAIT_CAN_NOT_WAIT; // goto afterSyscall // } loadModule("ThreadManForUser"); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(ThreadManForUser.class), "isDispatchThreadEnabled", "()Z"); Label returnError = new Label(); mv.visitJumpInsn(Opcodes.IFEQ, returnError); loadProcessor(); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Processor.class), "isInterruptsEnabled", "()Z"); Label noError = new Label(); mv.visitJumpInsn(Opcodes.IFNE, noError); mv.visitLabel(returnError); loadModuleLoggger(func); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Logger.class), "isDebugEnabled", "()Z"); Label notDebug = new Label(); mv.visitJumpInsn(Opcodes.IFEQ, notDebug); loadModuleLoggger(func); mv.visitLdcInsn(String.format("%s returning errorCode 0x%08X (ERROR_KERNEL_WAIT_CAN_NOT_WAIT)", func.getFunctionName(), SceKernelErrors.ERROR_KERNEL_WAIT_CAN_NOT_WAIT)); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Logger.class), "debug", "(" + Type.getDescriptor(Object.class) + ")V"); mv.visitLabel(notDebug); storeRegister(_v0, SceKernelErrors.ERROR_KERNEL_WAIT_CAN_NOT_WAIT); mv.visitJumpInsn(Opcodes.GOTO, afterSyscallLabel); mv.visitLabel(noError); } logSyscallStart(func); if (func.hasStackUsage()) { loadMemory(); loadRegister(_sp); loadImm(func.getStackUsage()); mv.visitInsn(Opcodes.ISUB); loadImm(0); loadImm(func.getStackUsage()); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, memoryInternalName, "memset", "(IBI)V"); } // Collecting the parameters and calling the module function... CompilerParameterReader parameterReader = new CompilerParameterReader(this); loadModule(func.getModuleName()); parameterReader.incrementCurrentStackSize(); Label tryStart = new Label(); Label tryEnd = new Label(); Label catchSceKernelErrorException = new Label(); mv.visitTryCatchBlock(tryStart, tryEnd, catchSceKernelErrorException, Type.getInternalName(SceKernelErrorException.class)); Class<?>[] parameterTypes = func.getHLEModuleMethod().getParameterTypes(); Class<?> returnType = func.getHLEModuleMethod().getReturnType(); StringBuilder methodDescriptor = new StringBuilder(); methodDescriptor.append("("); Annotation[][] paramsAnotations = func.getHLEModuleMethod().getParameterAnnotations(); int paramIndex = 0; for (Class<?> parameterType : parameterTypes) { methodDescriptor.append(Type.getDescriptor(parameterType)); loadParameter(parameterReader, func, parameterType, paramsAnotations[paramIndex], afterSyscallLabel, catchSceKernelErrorException); paramIndex++; } methodDescriptor.append(")"); methodDescriptor.append(Type.getDescriptor(returnType)); mv.visitLabel(tryStart); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(func.getHLEModuleMethod().getDeclaringClass()), func.getFunctionName(), methodDescriptor.toString()); storeReturnValue(func, returnType); if (parameterReader.hasErrorPointer()) { // errorPointer.setValue(0); mv.visitVarInsn(Opcodes.ALOAD, LOCAL_ERROR_POINTER); loadImm(0); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(TErrorPointer32.class), "setValue", "(I)V"); } loadRegister(_v0); logSyscallEnd(func, false); mv.visitInsn(Opcodes.POP); mv.visitLabel(tryEnd); mv.visitJumpInsn(Opcodes.GOTO, afterSyscallLabel); // catch (SceKernelErrorException e) { // errorCode = e.errorCode; // if (Modules.log.isDebugEnabled()) { // Modules.log.debug(String.format("<function name> return errorCode 0x%08X", errorCode)); // } // if (hasErrorPointer()) { // errorPointer.setValue(errorCode); // cpu.gpr[_v0] = 0; // } else { // cpu.gpr[_v0] = errorCode; // } // } mv.visitLabel(catchSceKernelErrorException); mv.visitFieldInsn(Opcodes.GETFIELD, Type.getInternalName(SceKernelErrorException.class), "errorCode", "I"); logSyscallEnd(func, true); if (parameterReader.hasErrorPointer()) { // errorPointer.setValue(errorCode); // cpu.gpr[_v0] = 0; mv.visitVarInsn(Opcodes.ALOAD, LOCAL_ERROR_POINTER); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(TErrorPointer32.class), "setValue", "(I)V"); storeRegister(_v0, 0); } else { // cpu.gpr[_v0] = errorCode; storeRegister(_v0); } // Reload the $ra register, the stack is lost after an exception CodeInstruction previousInstruction = codeBlock.getCodeInstruction(codeInstruction.getAddress() - 4); if (previousInstruction != null && previousInstruction.getInsn() == Instructions.JR) { int jumpRegister = (previousInstruction.getOpcode() >> 21) & 0x1F; loadRegister(jumpRegister); } mv.visitLabel(afterSyscallLabel); if (fastSyscall) { mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "postSyscallFast", "()V"); } else { mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "postSyscall", "()V"); } if (needFirmwareVersionCheck) { Label afterVersionCheckLabel = new Label(); mv.visitJumpInsn(Opcodes.GOTO, afterVersionCheckLabel); mv.visitLabel(unsupportedVersionLabel); loadModuleLoggger(func); mv.visitLdcInsn(String.format( "%s is not supported in firmware version %d, it requires at least firmware version %d", func.getFunctionName(), RuntimeContext.firmwareVersion, func.getFirmwareVersion())); mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, Type.getInternalName(Logger.class), "warn", "(" + Type.getDescriptor(Object.class) + ")V"); storeRegister(_v0, -1); mv.visitLabel(afterVersionCheckLabel); } }
From source file:jpcsp.Allegrex.compiler.CompilerContext.java
License:Open Source License
/** * Generate the required Java code to perform a syscall. * * When the syscall function is an HLEModuleFunctionReflection, * generate the code for calling the module function directly, as * HLEModuleFunctionReflection.execute() would. * * Otherwise, generate the code for calling * RuntimeContext.syscall()//from w w w.j a va2s . c o m * or * RuntimeContext.syscallFast() * * @param opcode opcode of the instruction */ public void visitSyscall(int opcode) { flushInstructionCount(false, false); int code = (opcode >> 6) & 0x000FFFFF; int syscallAddr = NIDMapper.getInstance().getAddressBySyscall(code); // Call the HLE method only when it has not been overwritten if (syscallAddr != 0) { if (log.isDebugEnabled()) { log.debug(String.format("Calling overwritten HLE method '%s' instead of syscall", NIDMapper.getInstance().getNameBySyscall(code))); } mv.visitMethodInsn(Opcodes.INVOKESTATIC, getClassName(syscallAddr, instanceIndex), getStaticExecMethodName(), getStaticExecMethodDesc()); } else { HLEModuleFunction func = HLEModuleManager.getInstance().getFunctionFromSyscallCode(code); boolean fastSyscall = isFastSyscall(code); // Under LLE, all syscalls are "fast" syscalls if (func == null && RuntimeContextLLE.isLLEActive()) { fastSyscall = true; } if (!fastSyscall) { storePc(); } boolean destroyTempRegisters = true; if (code == syscallLoadCoreUnmappedImport) { // We do not destroy the temp registers for special syscalls destroyTempRegisters = false; } if (func == null) { loadImm(code); if (fastSyscall) { mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "syscallFast", "(I)I"); } else { mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, "syscall", "(I)I"); } if (getCodeInstruction() != null) { if (getCodeInstruction().isDelaySlot()) { visitContinueToAddressInRegister(_ra); } else { visitContinueToAddress(getCodeInstruction().getAddress() + 4, false); } } else { mv.visitInsn(Opcodes.POP); } if (RuntimeContextLLE.isLLEActive()) { // We do not destroy the temp registers for LLE syscalls destroyTempRegisters = false; } } else { visitSyscall(func, fastSyscall); if (func.getNid() == HLESyscallNid || func.getNid() == InternalSyscallNid) { // We do not destroy the temp registers for special syscalls destroyTempRegisters = false; } } if (destroyTempRegisters) { // The following registers are always set to 0xDEADBEEF after a syscall int deadbeef = 0xDEADBEEF; storeRegister(_a0, deadbeef); storeRegister(_a1, deadbeef); storeRegister(_a2, deadbeef); storeRegister(_a3, deadbeef); storeRegister(_t0, deadbeef); storeRegister(_t1, deadbeef); storeRegister(_t2, deadbeef); storeRegister(_t3, deadbeef); storeRegister(_t4, deadbeef); storeRegister(_t5, deadbeef); storeRegister(_t6, deadbeef); storeRegister(_t7, deadbeef); storeRegister(_t8, deadbeef); storeRegister(_t9, deadbeef); prepareHiloForStore(); mv.visitLdcInsn(0xDEADBEEFDEADBEEFL); storeHilo(); } } // For code blocks consisting of a single syscall instruction, // generate an end for the code block. if (getCodeBlock().getLength() == 1) { loadRegister(_ra); visitJump(); } }
From source file:jpcsp.Allegrex.compiler.CompilerContext.java
License:Open Source License
public void checkSync() { if (RuntimeContext.enableDaemonThreadSync) { Label doNotWantSync = new Label(); mv.visitFieldInsn(Opcodes.GETSTATIC, runtimeContextInternalName, "wantSync", "Z"); mv.visitJumpInsn(Opcodes.IFEQ, doNotWantSync); mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, RuntimeContext.syncName, "()V"); mv.visitLabel(doNotWantSync);/* w w w . j a va 2s. co m*/ } }
From source file:jpcsp.Allegrex.compiler.CompilerContext.java
License:Open Source License
private void startInternalMethod() { // if (e != null) Label notReplacedLabel = new Label(); mv.visitFieldInsn(Opcodes.GETSTATIC, codeBlock.getClassName(), getReplaceFieldName(), executableDescriptor); mv.visitJumpInsn(Opcodes.IFNULL, notReplacedLabel); {//w ww . j a v a 2 s. c o m // return e.exec(returnAddress, alternativeReturnAddress, isJump); mv.visitFieldInsn(Opcodes.GETSTATIC, codeBlock.getClassName(), getReplaceFieldName(), executableDescriptor); mv.visitMethodInsn(Opcodes.INVOKEINTERFACE, executableInternalName, getExecMethodName(), getExecMethodDesc()); mv.visitInsn(Opcodes.IRETURN); } mv.visitLabel(notReplacedLabel); if (Profiler.isProfilerEnabled()) { loadImm(getCodeBlock().getStartAddress()); mv.visitMethodInsn(Opcodes.INVOKESTATIC, profilerInternalName, "addCall", "(I)V"); } if (RuntimeContext.debugCodeBlockCalls) { loadImm(getCodeBlock().getStartAddress()); mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, RuntimeContext.debugCodeBlockStart, "(I)V"); } }
From source file:jpcsp.Allegrex.compiler.CompilerContext.java
License:Open Source License
private void flushInstructionCount(boolean local, boolean last) { if (enableIntructionCounting) { if (local) { if (currentInstructionCount > 0) { mv.visitIincInsn(LOCAL_INSTRUCTION_COUNT, currentInstructionCount); }//from ww w .j a va 2 s . c om } else { mv.visitFieldInsn(Opcodes.GETSTATIC, runtimeContextInternalName, "currentThread", sceKernalThreadInfoDescriptor); mv.visitInsn(Opcodes.DUP); mv.visitFieldInsn(Opcodes.GETFIELD, sceKernalThreadInfoInternalName, "runClocks", "J"); loadLocalVar(LOCAL_INSTRUCTION_COUNT); if (currentInstructionCount > 0) { loadImm(currentInstructionCount); mv.visitInsn(Opcodes.IADD); } if (Profiler.isProfilerEnabled()) { mv.visitInsn(Opcodes.DUP); loadImm(getCodeBlock().getStartAddress()); mv.visitMethodInsn(Opcodes.INVOKESTATIC, profilerInternalName, "addInstructionCount", "(II)V"); } mv.visitInsn(Opcodes.I2L); mv.visitInsn(Opcodes.LADD); mv.visitFieldInsn(Opcodes.PUTFIELD, sceKernalThreadInfoInternalName, "runClocks", "J"); if (!last) { mv.visitInsn(Opcodes.ICONST_0); storeLocalVar(LOCAL_INSTRUCTION_COUNT); } } currentInstructionCount = 0; } }
From source file:jpcsp.Allegrex.compiler.CompilerContext.java
License:Open Source License
private void endInternalMethod() { if (RuntimeContext.debugCodeBlockCalls) { mv.visitInsn(Opcodes.DUP);// w w w. ja v a 2 s . c om loadImm(getCodeBlock().getStartAddress()); mv.visitInsn(Opcodes.SWAP); mv.visitMethodInsn(Opcodes.INVOKESTATIC, runtimeContextInternalName, RuntimeContext.debugCodeBlockEnd, "(II)V"); } }