Jump to content


Photo

Dpc's (a Possible Solution Against Freezes)


  • Please log in to reply
4 replies to this topic

#1 openxdkman

openxdkman

    X-S Genius

  • Moderator
  • PipPipPipPip
  • 823 posts
  • Xbox Version:unk
  • 360 version:unknown

Posted 14 June 2008 - 10:33 AM

Micro asked me about DPC's through PM, but it's better to reply publicly.
DPC means Delayed Procedure Call

You can see how are working DPC's in the source of OpenXDK :

C:\cygwin\usr\home\OpenXDK\src\hal\audio.c
or
C:\cygwin\usr\home\OpenXDK\src\hal\video.c

The goal is to not spend too much time in the code that handles a fired interrupt (or VERY bad things may occur, usually a nice impossible to understand freeze). So you schedule another call, which will be as long as you want, but later.

Progress around OpenXDK, as a whole, was gloomy for some time because of nasty issues, like Controller not responding, etc... It was due to a lack of DPC usage.

In your module you just need these declarations :

#include <xboxkrnl/xboxkrnl.h>

static KINTERRUPT InterruptObject;
static KDPC DPCObject;


To initialize :

KeInitializeDpc(&DPCObject,&DPC,NULL);



Inside your interrupt handler (be quick!) :

KeInsertQueueDpc(&DPCObject,NULL,NULL);

KeInsertQueueDpc queues Dpc and returns TRUE if Dpc not already queued. Dpc will be queued only once. So only one Dpc is fired after ISRs cease fire. The last parameters are the two SystemArgumentN pointers that can be passed to DPC later

Do only fast things that can't be delayed, like setting some Ack/Enable bit to respond to chipset correctly.



The code that handles the delayed procedure call (will be called by kernel later, in a safe way) :

static void __stdcall DPC(PKDPC Dpc,
PVOID DeferredContext,
PVOID SystemArgument1,
PVOID SystemArgument2)
{
You can take your time here! Of course interrupts can fire anytime, but they will just enqueue DPC's. DPC's are always launched one afther another. They don't interrupt each other, they won't be 'nested'.
DPCs avoid crashes inside non reentrant user callbacks called by nested ISRs. CAUTION : if you use fpu in DPC you have to save & restore yourself fpu state!!! (fpu=floating point unit, i.e the coprocessor executing floating point opcodes)

Do your lengthy stuff here. It's only safe here.
Typically you call a user defined callback
(think about saving/restoring fpu state).

return;
}



It's heavily used in all Microsoft operating systems.
If you are a XDK user, be aware it's used a lots of course, but you don't know it. Under OpenXDK, if you play with interrupts, you need to master DPC's yourself.

Edited by openxdkman, 14 June 2008 - 10:37 AM.


#2 Mię«os∞ft

Mię«os∞ft

    X-S Member

  • Members
  • Pip
  • 147 posts

Posted 14 June 2008 - 03:51 PM

This MOST probably will show my STUCK project some light love.gif

happy.gif

#3 Mię«os∞ft

Mię«os∞ft

    X-S Member

  • Members
  • Pip
  • 147 posts

Posted 23 June 2008 - 08:27 PM

What if the MAIN LOOP has to be a DPC? blink.gif

CODE

int _MainLoop()
{
   while (1)
   {
KeInsertQueueDpc(&myDPCObject,NULL,NULL);
   }
}

Is that OK? huh.gif
This atleast works but screen doesn't refresh so fast.... Also unstable.


When I do this, I get a blackscreen and all I see is "DPC call".
CODE


void XBoxStartup()
{
//inits
_MainLoop();
}

int _MainLoop()
{
    debugPrint(" DPC call"); //gets stuck?
KeInsertQueueDpc(&MYDPCObject,NULL,NULL);
}

static void __stdcall MYDPC(PKDPC Dpc,
PVOID DeferredContext,
PVOID SystemArgument1,
PVOID SystemArgument2)
{
    for (;;)
   {
///Lots and lots of code
   }
}

Edited by Mię«os∞ft, 23 June 2008 - 08:43 PM.


#4 Mię«os∞ft

Mię«os∞ft

    X-S Member

  • Members
  • Pip
  • 147 posts

Posted 23 June 2008 - 09:03 PM

QUOTE(Mię«os∞ft @ Jun 23 2008, 04:03 PM) View Post

CODE

void XBoxStartup()
{
//inits
_MainLoop();
}

int _MainLoop()
{
    debugPrint(" DPC call"); //gets stuck?
KeInsertQueueDpc(&MYDPCObject,NULL,NULL);
}

static void __stdcall MYDPC(PKDPC Dpc,
PVOID DeferredContext,
PVOID SystemArgument1,
PVOID SystemArgument2)
{
    for (;;)
   {
///Lots and lots of code
   }
}



Update: I removed all PB_PRINT stuff and replaced it with debugPrint.

Controller doesn't respond but I see the text printing. sad.gif

--

Controller works when DPC is removed tho :|

Edited by Mię«os∞ft, 23 June 2008 - 09:14 PM.


#5 openxdkman

openxdkman

    X-S Genius

  • Moderator
  • PipPipPipPip
  • 823 posts
  • Xbox Version:unk
  • 360 version:unknown

Posted 26 June 2008 - 10:00 PM

you don't initialize with this?
KeInitializeDpc(&MYDPCObject,&MYDPC,NULL);

also there is surely a limit, so don't enqueue an infinite number in no time




0 user(s) are reading this topic

0 members, 0 guests, 0 anonymous users