u32 sceKernelRegisterSubIntrHandler(u32 intrNumber, u32 subIntrNumber, u32 handler, u32 handlerArg) {
	if (intrNumber >= PSP_NUMBER_INTERRUPTS) {
		ERROR_LOG_REPORT(SCEINTC, "sceKernelRegisterSubIntrHandler(%i, %i, %08x, %08x): invalid interrupt", intrNumber, subIntrNumber, handler, handlerArg);
		return SCE_KERNEL_ERROR_ILLEGAL_INTRCODE;
	}
	if (subIntrNumber >= PSP_NUMBER_SUBINTERRUPTS) {
		ERROR_LOG_REPORT(SCEINTC, "sceKernelRegisterSubIntrHandler(%i, %i, %08x, %08x): invalid subinterrupt", intrNumber, subIntrNumber, handler, handlerArg);
		return SCE_KERNEL_ERROR_ILLEGAL_INTRCODE;
	}

	u32 error;
	SubIntrHandler *subIntrHandler = __RegisterSubIntrHandler(intrNumber, subIntrNumber, handler, handlerArg, error);
	if (subIntrHandler) {
		if (handler == 0) {
			WARN_LOG_REPORT(SCEINTC, "sceKernelRegisterSubIntrHandler(%i, %i, %08x, %08x): ignored NULL handler", intrNumber, subIntrNumber, handler, handlerArg);
		} else {
			DEBUG_LOG(SCEINTC, "sceKernelRegisterSubIntrHandler(%i, %i, %08x, %08x)", intrNumber, subIntrNumber, handler, handlerArg);
		}
	} else if (error = SCE_KERNEL_ERROR_FOUND_HANDLER) {
		ERROR_LOG_REPORT(SCEINTC, "sceKernelRegisterSubIntrHandler(%i, %i, %08x, %08x): duplicate handler", intrNumber, subIntrNumber, handler, handlerArg);
	} else {
		ERROR_LOG_REPORT(SCEINTC, "sceKernelRegisterSubIntrHandler(%i, %i, %08x, %08x): error %08x", intrNumber, subIntrNumber, handler, handlerArg, error);
	}
	return error;
}
u32 sceKernelRegisterSubIntrHandler(u32 intrNumber, u32 subIntrNumber, u32 handler, u32 handlerArg)
{
    DEBUG_LOG(HLE,"sceKernelRegisterSubIntrHandler(%i, %i, %08x, %08x)", intrNumber, subIntrNumber, handler, handlerArg);

    if (intrNumber >= PSP_NUMBER_INTERRUPTS)
        return -1;

    u32 error;
    SubIntrHandler *subIntrHandler = __RegisterSubIntrHandler(intrNumber, subIntrNumber, error);
    if (subIntrHandler)
    {
        subIntrHandler->enabled = false;
        subIntrHandler->handlerAddress = handler;
        subIntrHandler->handlerArg = handlerArg;
    }
    return error;
}
u32 sceKernelEnableSubIntr(u32 intrNumber, u32 subIntrNumber) {
	if (intrNumber >= PSP_NUMBER_INTERRUPTS) {
		ERROR_LOG_REPORT(SCEINTC, "sceKernelEnableSubIntr(%i, %i): invalid interrupt", intrNumber, subIntrNumber);
		return SCE_KERNEL_ERROR_ILLEGAL_INTRCODE;
	}
	if (subIntrNumber >= PSP_NUMBER_SUBINTERRUPTS) {
		ERROR_LOG_REPORT(SCEINTC, "sceKernelEnableSubIntr(%i, %i): invalid subinterrupt", intrNumber, subIntrNumber);
		return SCE_KERNEL_ERROR_ILLEGAL_INTRCODE;
	}

	DEBUG_LOG(SCEINTC, "sceKernelEnableSubIntr(%i, %i)", intrNumber, subIntrNumber);
	u32 error;
	if (!intrHandlers[intrNumber]->has(subIntrNumber)) {
		// Enableing a handler before registering it works fine.
		__RegisterSubIntrHandler(intrNumber, subIntrNumber, 0, 0, error);
	}

	intrHandlers[intrNumber]->enable(subIntrNumber);
	return 0;
}
Exemple #4
0
SceUID __KernelSetAlarm(u64 ticks, u32 handlerPtr, u32 commonPtr)
{
	if (!Memory::IsValidAddress(handlerPtr))
		return SCE_KERNEL_ERROR_ILLEGAL_ADDR;

	Alarm *alarm = new Alarm;
	SceUID uid = kernelObjects.Create(alarm);

	alarm->alm.size = NATIVEALARM_SIZE;
	alarm->alm.handlerPtr = handlerPtr;
	alarm->alm.commonPtr = commonPtr;

	u32 error;
	AlarmIntrHandler *handler = (AlarmIntrHandler *) __RegisterSubIntrHandler(PSP_SYSTIMER0_INTR, uid, error);
	if (error != 0)
	{
		kernelObjects.Destroy<Alarm>(uid);
		return error;
	}

	handler->setAlarm(alarm);
	__KernelScheduleAlarm(alarm, ticks);
	return uid;
}