03.01.2013 Views

Chapter 1

Chapter 1

Chapter 1

SHOW MORE
SHOW LESS

Create successful ePaper yourself

Turn your PDF publications into a flip-book with our unique Google optimized e-Paper software.

� Function() gives me the request code;<br />

� Int0(), Int1(), Int2(), and Int3() return the message parameters as integers;<br />

� Ptr0(), Ptr1(), Ptr2(), and Ptr3() return the message parameters as TAny*<br />

pointers;<br />

� Complete() completes the message, returning the TInt completion code.<br />

My philosophy here is to get beyond the shaky, type-unsafe stage as soon as possible. So I<br />

contain all knowledge of RMessage parameter numbers and types within ServiceL(), and<br />

call second-level handler functions, specified with type-safe parameters, to do the real work.<br />

Most second-level functions don't then need to use any RMessage-related functions at all.<br />

Those that do can get the current RMessage by using the server's Message() function.<br />

Error handling<br />

If the client request is malformed, we panic the client thread – just as we would panic our<br />

own thread if a conventional function call were made in error. The default case is handled<br />

by<br />

Server()->PanicClient(EBadRequest);<br />

This calls my CGsdpServer::PanicClient() function:<br />

void CGsdpServer::PanicClient(TInt aPanic) const<br />

}<br />

{<br />

// Let's have a look before we panic the client<br />

__DEBUGGER()<br />

// OK, go for it<br />

const_cast (Message().Client()).<br />

Panic(_L("GSDP-Server"),aPanic);<br />

The heart of this function is the RThread::Panic() call to panic the client thread, that is,<br />

the client for the message currently being processed.<br />

Until I put the __DEBUGGER() line in, it was impossible to analyze the cause of the panic<br />

under the emulator. The thread being panicked was in the middle of a send–receive function,<br />

somewhere in the kernel executive, and the corresponding debug information was not<br />

supplied in the SDK. However, the real cause of the panic is hidden inside the state of the<br />

server, so invoking the debugger from the server thread gives a much better clue about why<br />

the client thread was about to be panicked. The __DEBUGGER() macro only affects<br />

emulator debug builds, so I don't need to put any conditional compilation constructs around<br />

it.<br />

If the function servicing the client request leaves, then the CGsdpServer::RunError()<br />

function is called:<br />

TInt CGsdpServer::RunError(TInt aErr)<br />

{<br />

// if it's a bad descriptor, panic the client<br />

if (aErr==KErrBadDescriptor) // client had a bad descriptor<br />

{

Hooray! Your file is uploaded and ready to be published.

Saved successfully!

Ooh no, something went wrong!