Send data to user space daemon from kext

Hello,

I'm using kernel control API to send data to a user space daemon from kext. It works most of the time, but on some occation, the ctl_enqueuedata() function return the errno code 12(ENOMEM), which is a little weird. This is the snippet in my code.

// in kext
errno_t error = ctl_enqueuedata(gCtlInfo.clientCtlRef, gCtlInfo.unit, (void*)notify, sizeof(struct CONFIG_NOTIFY), CTL_DATA_EOR);
if (0 != error)
{
    KEXT_LOG_ERROR("Failed to talk to user space daemon(error=%d).", error);
    return result;
}

// in user space daemon
dispatch_source_t readSource = dispatch_source_create(DISPATCH_SOURCE_TYPE_READ, g_sock, 0, g_globalQueue);
dispatch_source_set_event_handler_f(readSource, (dispatch_function_t)dataArrived);
dispatch_resume(readSource);

ssize_t n = recv(sock, (void*)notify, sizeof(struct CONFIG_NOTIFY), 0);
if (n < sizeof(struct CONFIG_NOTIFY))
{
    SPDLOG_ERROR("recv() failed, error: {}", strerror(errno));
    return -1;
}


I just send a fixed-size struct from kext several times per minute, not much data I think. And I also set the buffer large enough in the kern_ctl_reg structure.

static struct kern_ctl_reg gCtlReg =
{
    BUNDLE_ID,
    0,
    0,
    0,
    0x800000, //2048KB
    0x800000,
    ctl_connect,
    ctl_disconnect,
    NULL,
    ctl_set,
    NULL 
};


BTW, my app runs on macOS 10.14.6 with 16GB ram.

What could be the possible reason for this failure? Thanks!

Replies

on some occation, the

ctl_enqueuedata
function return the errno code 12 (
ENOMEM
), which is a little weird.

That’s not that weird. When you write kernel code you must be careful to not generate unbounded amounts of data.

The approach I usually use in situations like this is to have the kernel code notify the user space client that data is available and then have the user space client request it. That means that the kernel code only passes data to the client when it’s actually ready to use it.

Share and Enjoy

Quinn “The Eskimo!”
Apple Developer Relations, Developer Technical Support, Core OS/Hardware

let myEmail = "eskimo" + "1" + "@apple.com"