• Open Menu Close Menu
  • Apple
  • Shopping Bag
  • Apple
  • Mac
  • iPad
  • iPhone
  • Watch
  • TV
  • Music
  • Support
  • Search apple.com
  • Shopping Bag

Lists

Open Menu Close Menu
  • Terms and Conditions
  • Lists hosted on this site
  • Email the Postmaster
  • Tips for posting to public mailing lists
Re: Why can an NSConnection only vend objects if sendPort == receivePort?
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Why can an NSConnection only vend objects if sendPort == receivePort?


  • Subject: Re: Why can an NSConnection only vend objects if sendPort == receivePort?
  • From: Wade Tregaskis <email@hidden>
  • Date: Mon, 1 Sep 2003 22:56:48 +1000

This is a followup to my previous email to add new information. I'm still yet to find a solution; indeed, as I'm about to show, I now have even less of an idea what the problem is.

This message is very long, because it includes some detailed debugging info. Sorry about the verbosity.

As I wrote previously:

Is it a design issue, or simply an arbitrary limit? I had hoped it were simply a case of over-zealous documentation, but it does indeed seem that NSConnections [where receive == send] cannot accept vended objects from the other end. The client port sends some data (78 bytes) to the server port, which then replies with a small amount of data (10 bytes). NSConnection's rootProxy method then returns nil to the client code. Further calls to rootProxy send the same data (with only the message count incremented), and receives the same reply (again, with only the message count incremented). I can't tell whether the server is returning some kind of error or the proxied object, but either way, the client isn't accepting it.

To append to this, I've found that even if I use NSConnection's in the proper way (server receive == send port, client has receive = nil, send == valid port) the behaviour is identical, only with an extra port in there making my debugging output more convoluted (on the up side, this did reveal a run loop issue I hadn't previously been able to reliably reproduce).

Anyway, the following is the debug output, with some comments added where explanation is necessary.

// connection is established, SSL stuff over and done with, all good to go
// Note that the 'bb1f0' at the start of each line simply denotes the run loop in which this is taking place; good for distinguishing between client(s) & server(s)
bb1f0 SecureSocketPort(a8a8c0) - sendBeforeDate:17h20m34s msgid:0 components:12ea690 from:aa18e0 reserved:0 // This is called by NSConnection, presumably
bb1f0 SecureSocketPort(a8a8c0) - isValid
bb1f0 SecureSocketPort(a8a8c0) - socketAvailable
bb1f0 {YES}
bb1f0 {YES}
bb1f0 SecureSocketPort(a8a8c0) - isConnected
bb1f0 {YES}
bb1f0 Connected and valid; sending message...
bb1f0 SecureSocketPort(aa18e0) - encodedForm
bb1f0 SecureSocketPort(aa18e0) - encodedString
bb1f0 {"131.172.83.106:49413"} // The 'from' port's local address
bb1f0 {<3133312e 3137322e 38332e31 30363a34 39343133 >} // The raw data form of the above string; that's all encodedForm does
bb1f0 Number of objects = 1 // [components count]
bb1f0 NSData - <04edfe1f 0e010b01 01010d4e 53496e76 6f636174 696f6e00 00010101 104e5344 69737461 6e744f62 6a656374 00000001 01010102 01010b72 6f6f744f 626a6563 74000101 0440403a 00014001 0000> // First component
bb1f0 No payload compression
bb1f0 Sending message // Writing to socket using SSLWrite
--- BlockCryptor::outputSize inSize 0x90 outSize 0x90 final 0 inBufSize 0x0
--- BlockCryptor::inputSize inSize 0x90 outSize 0x90 mInBufSize 0x0
=== BlockCryptor::update encrypt 1 inSize 0x90 outSize 0x90
bb1f0 SecureSocketPort - sslWriteFunction(b59270) // My write method, called by SecureTransport
bb1f0 SecureSocketPort(a8a8c0) - netsocketDataSent:b59270
bb1f0 Wrote 149 bytes // This line and the above confirm the data is being sent. Just in case anyone thought of asking. :)
bb1f0 {"No error"}
===SSLWrite: req 118 moved 118 status 0?
// etc

The result is the following:

// again, socket is already connected, SSL established, etc etc.
b446f0 SecureSocketPort(b56bc0) - netsocket:240d60 dataAvailable:149 // Got the same amount of data, as you'd expect
b446f0 SecureSocketPort(b56bc0) - isConnected
b446f0 {YES}
b446f0 SecureSocketPort - sslReadFunction(240d60)
b446f0 Read 5 bytes // My protocol has a 5-byte packet header
b446f0 {"No error"}
b446f0 SecureSocketPort - sslReadFunction(240d60)
b446f0 Read 144 bytes // Read the remaining data (payload)
b446f0 {"No error"}
--- BlockCryptor::outputSize inSize 0x90 outSize 0x90 final 0 inBufSize 0x0
--- BlockCryptor::inputSize inSize 0x90 outSize 0x90 mInBufSize 0x0
=== BlockCryptor::update encrypt 0 inSize 0x90 outSize 0x90
===SSLRead : req 5 moved 5 status 0?
===SSLRead : req 113 moved 113 status 0?
b446f0 Leaving payload uncompressed
b446f0 SecureSocketPort(b56bc0) - decodePacket:12e9160 // Decodes the actual payload; the message
b446f0 SecureSocketPort(b56bc0) - delegate
b446f0 {b45ba0}
b446f0 Message id = 0 // As was sent
b446f0 SecureSocketPort - secureSocketPortForAddress:"131.172.83.106:49413" // This address comes from the payload, and as you can see is the one we sent
b446f0 SecureSocketPort - secureSocketPortForHost:"131.172.83.106" port:49413
b446f0 Found existing instance 1281c40 // In this case I've taken a sample after several hundred message-reply cycles, so the return port already exists
b446f0 {1281c40}
b446f0 {1281c40}
b446f0 SecureSocketPort(1281c40) - isReady
b446f0 {YES}
b446f0 Number of objects = 1 // As expected
b446f0 NSData - <04edfe1f 0e010b01 01010d4e 53496e76 6f636174 696f6e00 00010101 104e5344 69737461 6e744f62 6a656374 00000001 01010102 01010b72 6f6f744f 626a6563 74000101 0440403a 00014001 0000> // This seems exactly the same as the data that was sent
b446f0 SecureSocketPort(b56bc0) - retain
b446f0 SecureSocketPort(1281c40) - retain
b446f0 Dispatching message to delegate // [[self delegate] handlePortMessage:....]
// Note that the delegate is taken as the connection passed in the addConnection:toRunLoop:forMode: method... this seems to work; I managed to break inside the code that was handling the message, and it shows NSConnection seems to be trying to deal with the message appropriately.
// etc

The delegate (the NSConnection in this case) then immediately sends a "reply" (without returning from handlePortMessage:), which looks a lot like what I've shown already, except that the single components NSData object is now:

b446f0 NSData - <04cefe2f 0e010b00 0000>

Again, this gets back to the client just fine:

bb1f0 NSData - <04cefe2f 0e010b00 0000>

And so on, ad infinum. I really wish I knew what this result is.. it seems awfully short to contain any meaningful data, but I don't otherwise know how to interpret it.

To be complete, I should assure you there is nothing wrong with how I'm trying to use DO - I've simply modified the SimpleThreads example from Apple, adding in the extra configuration stuff required on the ports, and little else. The server is setting a valid root object, and the NSConnection is accepting it. Yet the client NSConnection is definitely returning nil for rootProxy. As I mentioned, each call to rootProxy triggers the cycle detailed above, returning nil right after the short response is received, above.

I just cannot fathom what is not being done properly in my NSPort subclass.

FWIW, I'll be posting the source to this class very soon on Sourceforge, along with the modified SimpleThreads demo, if anyone wants a look themselves.

Wade Tregaskis
-- Sed quis custodiet ipsos custodes?
_______________________________________________
cocoa-dev mailing list | email@hidden
Help/Unsubscribe/Archives: http://www.lists.apple.com/mailman/listinfo/cocoa-dev
Do not post admin requests to the list. They will be ignored.

  • Prev by Date: Re: Application menu won't change
  • Next by Date: Enable the Copy Menu
  • Previous by thread: Re: (no subject)
  • Next by thread: Enable the Copy Menu
  • Index(es):
    • Date
    • Thread