Could I bind smartpointer to xpc connection?

I want to bind a smartpointer to xpc connection, will below work?

I have class A like this:

class A {
};

Initialization with xpc_connection currentConnection

auto aObj = std::make_shared<A>();
xpc_connection_set_context(currentConnection, aObj.get())

After I done with the connection, I get back the raw pointer:

auto pObj = reinterpret_cast<A*>(xpc_connection_get_context(currentConnection));
if (pObj != nullptr)
{
    std::shared_ptr<A> asmarter(pObj);
     asmarter.reset(); //release the smart pointer
}

Will this work?

Accepted Reply

I posted the screenshot since it contains the error information which might help understanding the problem.

In such situations it’s better to include a crash report. See Posting a Crash Report for details on post to post that.

that surfaceObj was from callback block of CGDisplayStreamCreateWithDispatchQueue, and its value is not null but not sure if it is valid.

If it’s not NULL then it’s definitely valid at the point that you got it. Keep in mind that it’s only valid until you return from the block that you pass to CGDisplayStreamCreateWithDispatchQueue. If you call IOSurfaceCreateXPCObject inside that block, it should be fine. If not, you’ll need to retain it until you make that call.

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

Replies

XPC objects, like xpc_connection_t, are reference counted. If you’re using Objective-C++, which is what I generally recommend, then ARC will take care of all this for you. If not, you’ll have to wrap this in some sort of infrastructure that:

  • Is initialised with a +1 object (or with a +0 object and then calls xpc_retain)

  • Calls xpc_release when you’re done.

I don’t know enough about C++ to comment on whether your specific smart pointer implementation meets these requirements.

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

Thanks, my project disabled the ARC (not under my control) and I have to release everything by myself except smart pointer, and it is mostly using C++ instead of Objective-C. If I send dictionary with content of xpc_dictionary_set_data, will retain keep the data memory from freeing immediately after releasing the dictionary, currently I'm sending data buffer to other side, I have to make a copy of the data in receiver side to avoid recv side data copying crash (does xpc recv use the data copy or share the data reference/pointer with sender?).

BTW, could I send CMSampleBufferRef via xpc_dictionary?


Steven

Never mind, I'm sending surface instead and it is working

How do I avoid  IOSurfaceCreateXPCObject crash? right now it is my headache issue.

Hmmm, I missed your response from a week ago. Sorry about that.

Back then you wrote:

my project disabled the ARC (not under my control)

)-:

If I send dictionary with content of xpc_dictionary_set_data, will retain keep the data memory from freeing immediately after releasing the dictionary

I don’t understand what you’ve written here. If you want to clarify it, perhaps with some code snippets, I’d be happy to take another. In the meantime, here’s my general response…

The beauty of Objective-C reference counting — and XPC objects inherit this design — is that you can reason about memory management locally. So, if you allocate a data object, you are responsible for releases it. If you set that as a property of on a dictionary, the dictionary has to make a reference (or a copy) and it’s responsible for releasing that.

currently I'm sending data buffer to other side, I have to make a copy of the data in receiver side to avoid recv side data copying crash

I don’t think you need to copy here — you could just as easily retain — but, yes, that’s the right approach. When your receive handler is called it’s passed a dictionary. The system holds a reference to that dictionary for the duration of the receive call. So, that dictionary, and any properties it references, are only guaranteed to persist until the point where you retain. If you need something to persist long, make a copy or add a reference.

(does xpc recv use the data copy or share the data reference/pointer with sender?).

XPC can both copy data and share data at the VM layer, depending on the specific circumstances.

Today you wrote:

I'm sending surface instead and it is working

I/O Surface is definitely your friend.

How do I avoid IOSurfaceCreateXPCObject crash?

It’s hard to tell from the snippet you posted. How do you construct surfaceObj?

ps Please post your code snippets using a code block (use triple backquotes delimiters, or use the Code Block button). That makes it much easier to read and reason about.

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

Thanks, I posted the screenshot since it contains the error information which might help understanding the problem.

BTW, that surfaceObj was from callback block of CGDisplayStreamCreateWithDispatchQueue, and its value is not null but not sure if it is valid.

auto dspref = CGDisplayStreamCreateWithDispatchQueue(
          displayId, 
          captureWidth, 
          captureHeight, 
          '420v', 
           opts,
           dispatch_queue_create("my_display_data", DISPATCH_QUEUE_SERIAL),
          ^( CGDisplayStreamFrameStatus status,  uint64_t time,  IOSurfaceRef surfaceObj,   CGDisplayStreamUpdateRef ref )
          {

'
Do we have any API to check if it is valid to avoid crash? Do we need release this surfaceObj after sent out the XPC message? I suppose system do the maintenance job for the callback block.

Again, ARC was disabled.

-Steven

I posted the screenshot since it contains the error information which might help understanding the problem.

In such situations it’s better to include a crash report. See Posting a Crash Report for details on post to post that.

that surfaceObj was from callback block of CGDisplayStreamCreateWithDispatchQueue, and its value is not null but not sure if it is valid.

If it’s not NULL then it’s definitely valid at the point that you got it. Keep in mind that it’s only valid until you return from the block that you pass to CGDisplayStreamCreateWithDispatchQueue. If you call IOSurfaceCreateXPCObject inside that block, it should be fine. If not, you’ll need to retain it until you make that call.

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"

Great, CFRetain fixed the occasional crash issue.

Thanks to Quinn :)

One extra question, same code of screen capture, xpc module of standalone video tool box H264 encoder (running in native M1 or Intel mode), the video quality of Intel is very good, but with M1, the video is way too blurry, anyone has idea of why this is happening?

the video quality of Intel is very good, but with M1, the video is way too blurry

No idea; I don’t really do graphics (-:

I recommend that you start a new thread with tags that are appropriate for the technologies you’re using.

Share and Enjoy

Quinn “The Eskimo!” @ Developer Technical Support @ Apple
let myEmail = "eskimo" + "1" + "@" + "apple.com"