2016-03-13 1 views
1

J'essaie de configurer un message mach pour envoyer une chaîne hors ligne en utilisant mach IPC. Cependant, j'obtiens une erreur (ipc/send) invalid msg-header lorsque j'essaie d'envoyer le message hors ligne.Configurer l'en-tête de message mach complexe

Voici la structure du message.

struct ool_msg 
{ 
    mach_msg_header_t header; 
    mach_msg_body_t body; 
    mach_msg_ool_descriptor_t data; 
    mach_msg_type_number_t count; 
}; 

Je configure l'en-tête comme ceci. La variable msg ci-dessous est un struct ool_msg.

hdr = &(msg.header); 
hdr->msgh_bits = MACH_MSGH_BITS_LOCAL(MACH_MSG_TYPE_COPY_SEND); 
hdr->msgh_bits |= MACH_MSGH_BITS_COMPLEX; 
hdr->msgh_size = sizeof(msg); 
hdr->msgh_local_port = MACH_PORT_NULL; 
hdr->msgh_remote_port = port; 

Voici comment je configure le reste du message Mach. Comment puis-je configurer correctement l'en-tête du message pour l'IPC Mach OCL?

Édition

Voici un programme qui reproduit mon problème.

#include <stdio.h> 
#include <mach/mach.h> 

static char *string = "123456789"; 

struct ool_msg 
{ 
    mach_msg_header_t header; 
    mach_msg_body_t body; 
    mach_msg_ool_descriptor_t data; 
    mach_msg_type_number_t count; 
}; 

int main(void) 
{ 
    kern_return_t err; 
    struct ool_msg msg; 
    mach_msg_header_t *hdr; 
    mach_port_t port = MACH_PORT_NULL; 

    err = mach_port_allocate(mach_task_self(), MACH_PORT_RIGHT_RECEIVE, &port); 
    if(err != KERN_SUCCESS) 
    { 
     mach_error("Can't allocate mach port\n", err); 
     return (-1); 
    } 

    err = mach_port_insert_right(mach_task_self(), port, port, 
           MACH_MSG_TYPE_MAKE_SEND); 
    if(err != KERN_SUCCESS) 
    { 
     mach_error("Can't insert port right\n", err); 
     return (-1); 
    } 

    hdr = &(msg.header); 
    hdr->msgh_bits = MACH_MSGH_BITS_LOCAL(MACH_MSG_TYPE_COPY_SEND); 
    hdr->msgh_bits |= MACH_MSGH_BITS_COMPLEX; 
    hdr->msgh_size = sizeof(msg); 
    hdr->msgh_local_port = MACH_PORT_NULL; 
    hdr->msgh_remote_port = port; 

    msg.body.msgh_descriptor_count = 1; 
    msg.data.address = string; 
    msg.data.size = strlen(string) + 1; 
    msg.data.deallocate = FALSE; 
    msg.data.copy = MACH_MSG_VIRTUAL_COPY; 
    msg.data.type = MACH_MSG_OOL_DESCRIPTOR; 
    msg.count = msg.data.size; 

    err = mach_msg(hdr, 
        MACH_SEND_MSG, 
        hdr->msgh_size, 
        0, 
        MACH_PORT_NULL, 
        MACH_MSG_TIMEOUT_NONE, 
        MACH_PORT_NULL); 
    if(err != KERN_SUCCESS) 
    { 
     mach_error("Can't send mach msg\n", err); 
     return (-1); 
    } 

    return (0); 
} 
+0

Comment exactement vous essayez d'envoyer la chaîne? Pourriez-vous créer un [exemple minimal, complet et vérifiable] (http://stackoverflow.com/help/mcve)? –

+0

@JoshdeKock J'ai ajouté un exemple. – 2trill2spill

Répondre

3

Comme the docs état:

MACH_MSGH_BITS_REMOTE et MACH_MSGH_BITS_LOCAL macros renvoient les valeurs mach_msg_type_name_t appropriées, étant donné une valeur msgh_bits. La macro MACH_MSGH_BITS construit une valeur pour msgh_bits, étant donné deux valeurs mach_msg_type_name_t.

Vous devez utiliser le MACH_MSGH_BITS macro plutôt que la macro MACH_MSGH_BITS_LOCAL lors du réglage du mach_msg_header_t.msgh_bits. Sinon, vous le réglez sur mach_msg_type_name_t par opposition au msgh_bits qui est celui que vous voulez.

Pour clarifier, vous avez besoin quelque chose comme la pièce suivante de code pour obtenir votre msgh_bits:

hdr->msgh_bits = MACH_MSGH_BITS(MACH_MSG_TYPE_COPY_SEND, MACH_MSG_TYPE_MAKE_SEND)