1/* 2 * Copyright (c) 2000-2005 Apple Computer, Inc. All rights reserved. 3 * 4 * @APPLE_OSREFERENCE_LICENSE_HEADER_START@ 5 * 6 * This file contains Original Code and/or Modifications of Original Code 7 * as defined in and that are subject to the Apple Public Source License 8 * Version 2.0 (the 'License'). You may not use this file except in 9 * compliance with the License. The rights granted to you under the License 10 * may not be used to create, or enable the creation or redistribution of, 11 * unlawful or unlicensed copies of an Apple operating system, or to 12 * circumvent, violate, or enable the circumvention or violation of, any 13 * terms of an Apple operating system software license agreement. 14 * 15 * Please obtain a copy of the License at 16 * http://www.opensource.apple.com/apsl/ and read it before using this file. 17 * 18 * The Original Code and all software distributed under the License are 19 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER 20 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, 21 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, 22 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT. 23 * Please see the License for the specific language governing rights and 24 * limitations under the License. 25 * 26 * @APPLE_OSREFERENCE_LICENSE_HEADER_END@ 27 */ 28/* 29 * @OSF_COPYRIGHT@ 30 */ 31/* 32 * Mach Operating System 33 * Copyright (c) 1991,1990,1989,1988,1987 Carnegie Mellon University 34 * All Rights Reserved. 35 * 36 * Permission to use, copy, modify and distribute this software and its 37 * documentation is hereby granted, provided that both the copyright 38 * notice and this permission notice appear in all copies of the 39 * software, derivative works or modified versions, and any portions 40 * thereof, and that both notices appear in supporting documentation. 41 * 42 * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS" 43 * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR 44 * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE. 45 * 46 * Carnegie Mellon requests users of this software to return to 47 * 48 * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU 49 * School of Computer Science 50 * Carnegie Mellon University 51 * Pittsburgh PA 15213-3890 52 * 53 * any improvements or extensions that they make and grant Carnegie Mellon 54 * the rights to redistribute these changes. 55 */ 56/* 57 * NOTICE: This file was modified by McAfee Research in 2004 to introduce 58 * support for mandatory and extensible security protections. This notice 59 * is included in support of clause 2.2 (b) of the Apple Public License, 60 * Version 2.0. 61 * Copyright (c) 2005 SPARTA, Inc. 62 */ 63/* 64 */ 65/* 66 * File: mach/message.h 67 * 68 * Mach IPC message and primitive function definitions. 69 */ 70 71#ifndef _MACH_MESSAGE_H_ 72#define _MACH_MESSAGE_H_ 73 74#include <stdint.h> 75#include <mach/port.h> 76#include <mach/boolean.h> 77#include <mach/kern_return.h> 78#include <mach/machine/vm_types.h> 79 80#include <sys/cdefs.h> 81#include <sys/appleapiopts.h> 82 83/* 84 * The timeout mechanism uses mach_msg_timeout_t values, 85 * passed by value. The timeout units are milliseconds. 86 * It is controlled with the MACH_SEND_TIMEOUT 87 * and MACH_RCV_TIMEOUT options. 88 */ 89 90typedef natural_t mach_msg_timeout_t; 91 92/* 93 * The value to be used when there is no timeout. 94 * (No MACH_SEND_TIMEOUT/MACH_RCV_TIMEOUT option.) 95 */ 96 97#define MACH_MSG_TIMEOUT_NONE ((mach_msg_timeout_t) 0) 98 99/* 100 * The kernel uses MACH_MSGH_BITS_COMPLEX as a hint. If it isn't on, it 101 * assumes the body of the message doesn't contain port rights or OOL 102 * data. The field is set in received messages. A user task must 103 * use caution in interpreting the body of a message if the bit isn't 104 * on, because the mach_msg_type's in the body might "lie" about the 105 * contents. If the bit isn't on, but the mach_msg_types 106 * in the body specify rights or OOL data, the behavior is undefined. 107 * (Ie, an error may or may not be produced.) 108 * 109 * The value of MACH_MSGH_BITS_REMOTE determines the interpretation 110 * of the msgh_remote_port field. It is handled like a msgt_name. 111 * 112 * The value of MACH_MSGH_BITS_LOCAL determines the interpretation 113 * of the msgh_local_port field. It is handled like a msgt_name. 114 * 115 * MACH_MSGH_BITS() combines two MACH_MSG_TYPE_* values, for the remote 116 * and local fields, into a single value suitable for msgh_bits. 117 * 118 * MACH_MSGH_BITS_CIRCULAR should be zero; is is used internally. 119 * 120 * The unused bits should be zero and are reserved for the kernel 121 * or for future interface expansion. 122 */ 123 124#define MACH_MSGH_BITS_ZERO 0x00000000 125#define MACH_MSGH_BITS_REMOTE_MASK 0x000000ff 126#define MACH_MSGH_BITS_LOCAL_MASK 0x0000ff00 127#define MACH_MSGH_BITS_COMPLEX 0x80000000U 128#define MACH_MSGH_BITS_USER 0x8000ffffU 129 130#define MACH_MSGH_BITS_CIRCULAR 0x40000000 /* internal use only */ 131#define MACH_MSGH_BITS_USED 0xc000ffffU 132 133#define MACH_MSGH_BITS_PORTS_MASK \ 134 (MACH_MSGH_BITS_REMOTE_MASK|MACH_MSGH_BITS_LOCAL_MASK) 135 136#define MACH_MSGH_BITS(remote, local) \ 137 ((remote) | ((local) << 8)) 138#define MACH_MSGH_BITS_REMOTE(bits) \ 139 ((bits) & MACH_MSGH_BITS_REMOTE_MASK) 140#define MACH_MSGH_BITS_LOCAL(bits) \ 141 (((bits) & MACH_MSGH_BITS_LOCAL_MASK) >> 8) 142#define MACH_MSGH_BITS_PORTS(bits) \ 143 ((bits) & MACH_MSGH_BITS_PORTS_MASK) 144#define MACH_MSGH_BITS_OTHER(bits) \ 145 ((bits) &~ MACH_MSGH_BITS_PORTS_MASK) 146 147/* 148 * Every message starts with a message header. 149 * Following the message header, if the message is complex, are a count 150 * of type descriptors and the type descriptors themselves 151 * (mach_msg_descriptor_t). The size of the message must be specified in 152 * bytes, and includes the message header, descriptor count, descriptors, 153 * and inline data. 154 * 155 * The msgh_remote_port field specifies the destination of the message. 156 * It must specify a valid send or send-once right for a port. 157 * 158 * The msgh_local_port field specifies a "reply port". Normally, 159 * This field carries a send-once right that the receiver will use 160 * to reply to the message. It may carry the values MACH_PORT_NULL, 161 * MACH_PORT_DEAD, a send-once right, or a send right. 162 * 163 * The msgh_seqno field carries a sequence number associated with the 164 * received-from port. A port's sequence number is incremented every 165 * time a message is received from it. In sent messages, the field's 166 * value is ignored. 167 * 168 * The msgh_id field is uninterpreted by the message primitives. 169 * It normally carries information specifying the format 170 * or meaning of the message. 171 */ 172 173typedef unsigned int mach_msg_bits_t; 174typedef natural_t mach_msg_size_t; 175typedef integer_t mach_msg_id_t; 176 177 178#define MACH_MSG_SIZE_NULL (mach_msg_size_t *) 0 179 180typedef unsigned int mach_msg_type_name_t; 181 182#define MACH_MSG_TYPE_MOVE_RECEIVE 16 /* Must hold receive rights */ 183#define MACH_MSG_TYPE_MOVE_SEND 17 /* Must hold send rights */ 184#define MACH_MSG_TYPE_MOVE_SEND_ONCE 18 /* Must hold sendonce rights */ 185#define MACH_MSG_TYPE_COPY_SEND 19 /* Must hold send rights */ 186#define MACH_MSG_TYPE_MAKE_SEND 20 /* Must hold receive rights */ 187#define MACH_MSG_TYPE_MAKE_SEND_ONCE 21 /* Must hold receive rights */ 188#define MACH_MSG_TYPE_COPY_RECEIVE 22 /* Must hold receive rights */ 189 190typedef unsigned int mach_msg_copy_options_t; 191 192#define MACH_MSG_PHYSICAL_COPY 0 193#define MACH_MSG_VIRTUAL_COPY 1 194#define MACH_MSG_ALLOCATE 2 195#define MACH_MSG_OVERWRITE 3 196#ifdef MACH_KERNEL 197#define MACH_MSG_KALLOC_COPY_T 4 198#endif /* MACH_KERNEL */ 199 200/* 201 * In a complex mach message, the mach_msg_header_t is followed by 202 * a descriptor count, then an array of that number of descriptors 203 * (mach_msg_*_descriptor_t). The type field of mach_msg_type_descriptor_t 204 * (which any descriptor can be cast to) indicates the flavor of the 205 * descriptor. 206 * 207 * Note that in LP64, the various types of descriptors are no longer all 208 * the same size as mach_msg_descriptor_t, so the array cannot be indexed 209 * as expected. 210 */ 211 212typedef unsigned int mach_msg_descriptor_type_t; 213 214#define MACH_MSG_PORT_DESCRIPTOR 0 215#define MACH_MSG_OOL_DESCRIPTOR 1 216#define MACH_MSG_OOL_PORTS_DESCRIPTOR 2 217#define MACH_MSG_OOL_VOLATILE_DESCRIPTOR 3 218 219#pragma pack(4) 220 221typedef struct 222{ 223 natural_t pad1; 224 mach_msg_size_t pad2; 225 unsigned int pad3 : 24; 226 mach_msg_descriptor_type_t type : 8; 227} mach_msg_type_descriptor_t; 228 229typedef struct 230{ 231 mach_port_t name; 232#if !(defined(KERNEL) && defined(__LP64__)) 233// Pad to 8 bytes everywhere except the K64 kernel where mach_port_t is 8 bytes 234 mach_msg_size_t pad1; 235#endif 236 unsigned int pad2 : 16; 237 mach_msg_type_name_t disposition : 8; 238 mach_msg_descriptor_type_t type : 8; 239#if defined(KERNEL) 240 uint32_t pad_end; 241#endif 242} mach_msg_port_descriptor_t; 243 244typedef struct 245{ 246 uint32_t address; 247 mach_msg_size_t size; 248 boolean_t deallocate: 8; 249 mach_msg_copy_options_t copy: 8; 250 unsigned int pad1: 8; 251 mach_msg_descriptor_type_t type: 8; 252} mach_msg_ool_descriptor32_t; 253 254typedef struct 255{ 256 uint64_t address; 257 boolean_t deallocate: 8; 258 mach_msg_copy_options_t copy: 8; 259 unsigned int pad1: 8; 260 mach_msg_descriptor_type_t type: 8; 261 mach_msg_size_t size; 262} mach_msg_ool_descriptor64_t; 263 264typedef struct 265{ 266 void* address; 267#if !defined(__LP64__) 268 mach_msg_size_t size; 269#endif 270 boolean_t deallocate: 8; 271 mach_msg_copy_options_t copy: 8; 272 unsigned int pad1: 8; 273 mach_msg_descriptor_type_t type: 8; 274#if defined(__LP64__) 275 mach_msg_size_t size; 276#endif 277#if defined(KERNEL) && !defined(__LP64__) 278 uint32_t pad_end; 279#endif 280} mach_msg_ool_descriptor_t; 281 282typedef struct 283{ 284 uint32_t address; 285 mach_msg_size_t count; 286 boolean_t deallocate: 8; 287 mach_msg_copy_options_t copy: 8; 288 mach_msg_type_name_t disposition : 8; 289 mach_msg_descriptor_type_t type : 8; 290} mach_msg_ool_ports_descriptor32_t; 291 292typedef struct 293{ 294 uint64_t address; 295 boolean_t deallocate: 8; 296 mach_msg_copy_options_t copy: 8; 297 mach_msg_type_name_t disposition : 8; 298 mach_msg_descriptor_type_t type : 8; 299 mach_msg_size_t count; 300} mach_msg_ool_ports_descriptor64_t; 301 302typedef struct 303{ 304 void* address; 305#if !defined(__LP64__) 306 mach_msg_size_t count; 307#endif 308 boolean_t deallocate: 8; 309 mach_msg_copy_options_t copy: 8; 310 mach_msg_type_name_t disposition : 8; 311 mach_msg_descriptor_type_t type : 8; 312#if defined(__LP64__) 313 mach_msg_size_t count; 314#endif 315#if defined(KERNEL) && !defined(__LP64__) 316 uint32_t pad_end; 317#endif 318} mach_msg_ool_ports_descriptor_t; 319 320/* 321 * LP64support - This union definition is not really 322 * appropriate in LP64 mode because not all descriptors 323 * are of the same size in that environment. 324 */ 325#if defined(__LP64__) && defined(KERNEL) 326typedef union 327{ 328 mach_msg_port_descriptor_t port; 329 mach_msg_ool_descriptor32_t out_of_line; 330 mach_msg_ool_ports_descriptor32_t ool_ports; 331 mach_msg_type_descriptor_t type; 332} mach_msg_descriptor_t; 333#else 334typedef union 335{ 336 mach_msg_port_descriptor_t port; 337 mach_msg_ool_descriptor_t out_of_line; 338 mach_msg_ool_ports_descriptor_t ool_ports; 339 mach_msg_type_descriptor_t type; 340} mach_msg_descriptor_t; 341#endif 342 343typedef struct 344{ 345 mach_msg_size_t msgh_descriptor_count; 346} mach_msg_body_t; 347 348#define MACH_MSG_BODY_NULL (mach_msg_body_t *) 0 349#define MACH_MSG_DESCRIPTOR_NULL (mach_msg_descriptor_t *) 0 350 351typedef struct 352{ 353 mach_msg_bits_t msgh_bits; 354 mach_msg_size_t msgh_size; 355 mach_port_t msgh_remote_port; 356 mach_port_t msgh_local_port; 357 mach_msg_size_t msgh_reserved; 358 mach_msg_id_t msgh_id; 359} mach_msg_header_t; 360 361#define MACH_MSG_NULL (mach_msg_header_t *) 0 362 363typedef struct 364{ 365 mach_msg_header_t header; 366 mach_msg_body_t body; 367} mach_msg_base_t; 368 369typedef unsigned int mach_msg_trailer_type_t; 370 371#define MACH_MSG_TRAILER_FORMAT_0 0 372 373typedef unsigned int mach_msg_trailer_size_t; 374 375typedef struct 376{ 377 mach_msg_trailer_type_t msgh_trailer_type; 378 mach_msg_trailer_size_t msgh_trailer_size; 379} mach_msg_trailer_t; 380 381typedef struct 382{ 383 mach_msg_trailer_type_t msgh_trailer_type; 384 mach_msg_trailer_size_t msgh_trailer_size; 385 mach_port_seqno_t msgh_seqno; 386} mach_msg_seqno_trailer_t; 387 388typedef struct 389{ 390 unsigned int val[2]; 391} security_token_t; 392 393typedef struct 394{ 395 mach_msg_trailer_type_t msgh_trailer_type; 396 mach_msg_trailer_size_t msgh_trailer_size; 397 mach_port_seqno_t msgh_seqno; 398 security_token_t msgh_sender; 399} mach_msg_security_trailer_t; 400 401/* 402 * The audit token is an opaque token which identifies 403 * Mach tasks and senders of Mach messages as subjects 404 * to the BSM audit system. Only the appropriate BSM 405 * library routines should be used to interpret the 406 * contents of the audit token as the representation 407 * of the subject identity within the token may change 408 * over time. 409 */ 410typedef struct 411{ 412 unsigned int val[8]; 413} audit_token_t; 414 415typedef struct 416{ 417 mach_msg_trailer_type_t msgh_trailer_type; 418 mach_msg_trailer_size_t msgh_trailer_size; 419 mach_port_seqno_t msgh_seqno; 420 security_token_t msgh_sender; 421 audit_token_t msgh_audit; 422} mach_msg_audit_trailer_t; 423 424typedef struct 425{ 426 mach_msg_trailer_type_t msgh_trailer_type; 427 mach_msg_trailer_size_t msgh_trailer_size; 428 mach_port_seqno_t msgh_seqno; 429 security_token_t msgh_sender; 430 audit_token_t msgh_audit; 431 mach_port_context_t msgh_context; 432} mach_msg_context_trailer_t; 433 434typedef struct 435{ 436 mach_port_name_t sender; 437} msg_labels_t; 438 439/* 440 Trailer type to pass MAC policy label info as a mach message trailer. 441 442*/ 443 444typedef struct 445{ 446 mach_msg_trailer_type_t msgh_trailer_type; 447 mach_msg_trailer_size_t msgh_trailer_size; 448 mach_port_seqno_t msgh_seqno; 449 security_token_t msgh_sender; 450 audit_token_t msgh_audit; 451 mach_port_context_t msgh_context; 452 int msgh_ad; 453 msg_labels_t msgh_labels; 454} mach_msg_mac_trailer_t; 455 456#define MACH_MSG_TRAILER_MINIMUM_SIZE sizeof(mach_msg_trailer_t) 457 458/* 459 * These values can change from release to release - but clearly 460 * code cannot request additional trailer elements one was not 461 * compiled to understand. Therefore, it is safe to use this 462 * constant when the same module specified the receive options. 463 * Otherwise, you run the risk that the options requested by 464 * another module may exceed the local modules notion of 465 * MAX_TRAILER_SIZE. 466 */ 467typedef mach_msg_mac_trailer_t mach_msg_max_trailer_t; 468#define MAX_TRAILER_SIZE ((mach_msg_size_t)sizeof(mach_msg_max_trailer_t)) 469 470/* 471 * Legacy requirements keep us from ever updating these defines (even 472 * when the format_0 trailers gain new option data fields in the future). 473 * Therefore, they shouldn't be used going forward. Instead, the sizes 474 * should be compared against the specific element size requested using 475 * REQUESTED_TRAILER_SIZE. 476 */ 477typedef mach_msg_security_trailer_t mach_msg_format_0_trailer_t; 478 479/*typedef mach_msg_mac_trailer_t mach_msg_format_0_trailer_t; 480*/ 481 482#define MACH_MSG_TRAILER_FORMAT_0_SIZE sizeof(mach_msg_format_0_trailer_t) 483 484#define KERNEL_SECURITY_TOKEN_VALUE { {0, 1} } 485extern security_token_t KERNEL_SECURITY_TOKEN; 486 487#define KERNEL_AUDIT_TOKEN_VALUE { {0, 0, 0, 0, 0, 0, 0, 0} } 488extern audit_token_t KERNEL_AUDIT_TOKEN; 489 490typedef integer_t mach_msg_options_t; 491 492typedef struct 493{ 494 mach_msg_header_t header; 495} mach_msg_empty_send_t; 496 497typedef struct 498{ 499 mach_msg_header_t header; 500 mach_msg_trailer_t trailer; 501} mach_msg_empty_rcv_t; 502 503typedef union 504{ 505 mach_msg_empty_send_t send; 506 mach_msg_empty_rcv_t rcv; 507} mach_msg_empty_t; 508 509#pragma pack() 510 511/* utility to round the message size - will become machine dependent */ 512#define round_msg(x) (((mach_msg_size_t)(x) + sizeof (natural_t) - 1) & \ 513 ~(sizeof (natural_t) - 1)) 514 515/* 516 * There is no fixed upper bound to the size of Mach messages. 517 */ 518#define MACH_MSG_SIZE_MAX ((mach_msg_size_t) ~0) 519 520#if defined(__APPLE_API_PRIVATE) 521/* 522 * But architectural limits of a given implementation, or 523 * temporal conditions may cause unpredictable send failures 524 * for messages larger than MACH_MSG_SIZE_RELIABLE. 525 * 526 * In either case, waiting for memory is [currently] outside 527 * the scope of send timeout values provided to IPC. 528 */ 529#define MACH_MSG_SIZE_RELIABLE ((mach_msg_size_t) 256 * 1024) 530#endif 531/* 532 * Compatibility definitions, for code written 533 * when there was a msgh_kind instead of msgh_seqno. 534 */ 535#define MACH_MSGH_KIND_NORMAL 0x00000000 536#define MACH_MSGH_KIND_NOTIFICATION 0x00000001 537#define msgh_kind msgh_seqno 538#define mach_msg_kind_t mach_port_seqno_t 539 540typedef natural_t mach_msg_type_size_t; 541typedef natural_t mach_msg_type_number_t; 542 543/* 544 * Values received/carried in messages. Tells the receiver what 545 * sort of port right they now have. 546 * 547 * MACH_MSG_TYPE_PORT_NAME is used to transfer a port name 548 * which should remain uninterpreted by the kernel. (Port rights 549 * are not transferred, just the port name.) 550 */ 551 552#define MACH_MSG_TYPE_PORT_NONE 0 553 554#define MACH_MSG_TYPE_PORT_NAME 15 555#define MACH_MSG_TYPE_PORT_RECEIVE MACH_MSG_TYPE_MOVE_RECEIVE 556#define MACH_MSG_TYPE_PORT_SEND MACH_MSG_TYPE_MOVE_SEND 557#define MACH_MSG_TYPE_PORT_SEND_ONCE MACH_MSG_TYPE_MOVE_SEND_ONCE 558 559#define MACH_MSG_TYPE_LAST 22 /* Last assigned */ 560 561/* 562 * A dummy value. Mostly used to indicate that the actual value 563 * will be filled in later, dynamically. 564 */ 565 566#define MACH_MSG_TYPE_POLYMORPHIC ((mach_msg_type_name_t) -1) 567 568/* 569 * Is a given item a port type? 570 */ 571 572#define MACH_MSG_TYPE_PORT_ANY(x) \ 573 (((x) >= MACH_MSG_TYPE_MOVE_RECEIVE) && \ 574 ((x) <= MACH_MSG_TYPE_MAKE_SEND_ONCE)) 575 576#define MACH_MSG_TYPE_PORT_ANY_SEND(x) \ 577 (((x) >= MACH_MSG_TYPE_MOVE_SEND) && \ 578 ((x) <= MACH_MSG_TYPE_MAKE_SEND_ONCE)) 579 580#define MACH_MSG_TYPE_PORT_ANY_RIGHT(x) \ 581 (((x) >= MACH_MSG_TYPE_MOVE_RECEIVE) && \ 582 ((x) <= MACH_MSG_TYPE_MOVE_SEND_ONCE)) 583 584typedef integer_t mach_msg_option_t; 585 586#define MACH_MSG_OPTION_NONE 0x00000000 587 588#define MACH_SEND_MSG 0x00000001 589#define MACH_RCV_MSG 0x00000002 590#define MACH_RCV_LARGE 0x00000004 591 592#define MACH_SEND_TIMEOUT 0x00000010 593#define MACH_SEND_INTERRUPT 0x00000040 /* libmach implements */ 594#define MACH_SEND_NOTIFY 0x00000080 /* arm send-possible notify */ 595#define MACH_SEND_ALWAYS 0x00010000 /* internal use only */ 596#define MACH_SEND_TRAILER 0x00020000 597 598#define MACH_RCV_TIMEOUT 0x00000100 599#define MACH_RCV_NOTIFY 0x00000200 /* reserved - legacy */ 600#define MACH_RCV_INTERRUPT 0x00000400 /* libmach implements */ 601#define MACH_RCV_OVERWRITE 0x00001000 602 603/* 604 * NOTE: a 0x00------ RCV mask implies to ask for 605 * a MACH_MSG_TRAILER_FORMAT_0 with 0 Elements, 606 * which is equivalent to a mach_msg_trailer_t. 607 * 608 * XXXMAC: unlike the rest of the MACH_RCV_* flags, MACH_RCV_TRAILER_LABELS 609 * needs its own private bit since we only calculate its fields when absolutely 610 * required. 611 */ 612#define MACH_RCV_TRAILER_NULL 0 613#define MACH_RCV_TRAILER_SEQNO 1 614#define MACH_RCV_TRAILER_SENDER 2 615#define MACH_RCV_TRAILER_AUDIT 3 616#define MACH_RCV_TRAILER_CTX 4 617#define MACH_RCV_TRAILER_AV 7 618#define MACH_RCV_TRAILER_LABELS 8 619 620#define MACH_RCV_TRAILER_TYPE(x) (((x) & 0xf) << 28) 621#define MACH_RCV_TRAILER_ELEMENTS(x) (((x) & 0xf) << 24) 622#define MACH_RCV_TRAILER_MASK ((0xff << 24)) 623 624#define GET_RCV_ELEMENTS(y) (((y) >> 24) & 0xf) 625 626/* 627 * XXXMAC: note that in the case of MACH_RCV_TRAILER_LABELS, 628 * we just fall through to mach_msg_max_trailer_t. 629 * This is correct behavior since mach_msg_max_trailer_t is defined as 630 * mac_msg_mac_trailer_t which is used for the LABELS trailer. 631 * It also makes things work properly if MACH_RCV_TRAILER_LABELS is ORed 632 * with one of the other options. 633 */ 634 635#define REQUESTED_TRAILER_SIZE_NATIVE(y) \ 636 ((mach_msg_trailer_size_t) \ 637 ((GET_RCV_ELEMENTS(y) == MACH_RCV_TRAILER_NULL) ? \ 638 sizeof(mach_msg_trailer_t) : \ 639 ((GET_RCV_ELEMENTS(y) == MACH_RCV_TRAILER_SEQNO) ? \ 640 sizeof(mach_msg_seqno_trailer_t) : \ 641 ((GET_RCV_ELEMENTS(y) == MACH_RCV_TRAILER_SENDER) ? \ 642 sizeof(mach_msg_security_trailer_t) : \ 643 ((GET_RCV_ELEMENTS(y) == MACH_RCV_TRAILER_AUDIT) ? \ 644 sizeof(mach_msg_audit_trailer_t) : \ 645 ((GET_RCV_ELEMENTS(y) == MACH_RCV_TRAILER_CTX) ? \ 646 sizeof(mach_msg_context_trailer_t) : \ 647 ((GET_RCV_ELEMENTS(y) == MACH_RCV_TRAILER_AV) ? \ 648 sizeof(mach_msg_mac_trailer_t) : \ 649 sizeof(mach_msg_max_trailer_t)))))))) 650 651 652#ifdef XNU_KERNEL_PRIVATE 653 654#define REQUESTED_TRAILER_SIZE(is64, y) REQUESTED_TRAILER_SIZE_NATIVE(y) 655 656#else /* XNU_KERNEL_PRIVATE */ 657#define REQUESTED_TRAILER_SIZE(y) REQUESTED_TRAILER_SIZE_NATIVE(y) 658#endif /* XNU_KERNEL_PRIVATE */ 659 660/* 661 * Much code assumes that mach_msg_return_t == kern_return_t. 662 * This definition is useful for descriptive purposes. 663 * 664 * See <mach/error.h> for the format of error codes. 665 * IPC errors are system 4. Send errors are subsystem 0; 666 * receive errors are subsystem 1. The code field is always non-zero. 667 * The high bits of the code field communicate extra information 668 * for some error codes. MACH_MSG_MASK masks off these special bits. 669 */ 670 671typedef kern_return_t mach_msg_return_t; 672 673#define MACH_MSG_SUCCESS 0x00000000 674 675 676#define MACH_MSG_MASK 0x00003e00 677 /* All special error code bits defined below. */ 678#define MACH_MSG_IPC_SPACE 0x00002000 679 /* No room in IPC name space for another capability name. */ 680#define MACH_MSG_VM_SPACE 0x00001000 681 /* No room in VM address space for out-of-line memory. */ 682#define MACH_MSG_IPC_KERNEL 0x00000800 683 /* Kernel resource shortage handling an IPC capability. */ 684#define MACH_MSG_VM_KERNEL 0x00000400 685 /* Kernel resource shortage handling out-of-line memory. */ 686 687#define MACH_SEND_IN_PROGRESS 0x10000001 688 /* Thread is waiting to send. (Internal use only.) */ 689#define MACH_SEND_INVALID_DATA 0x10000002 690 /* Bogus in-line data. */ 691#define MACH_SEND_INVALID_DEST 0x10000003 692 /* Bogus destination port. */ 693#define MACH_SEND_TIMED_OUT 0x10000004 694 /* Message not sent before timeout expired. */ 695#define MACH_SEND_INTERRUPTED 0x10000007 696 /* Software interrupt. */ 697#define MACH_SEND_MSG_TOO_SMALL 0x10000008 698 /* Data doesn't contain a complete message. */ 699#define MACH_SEND_INVALID_REPLY 0x10000009 700 /* Bogus reply port. */ 701#define MACH_SEND_INVALID_RIGHT 0x1000000a 702 /* Bogus port rights in the message body. */ 703#define MACH_SEND_INVALID_NOTIFY 0x1000000b 704 /* Bogus notify port argument. */ 705#define MACH_SEND_INVALID_MEMORY 0x1000000c 706 /* Invalid out-of-line memory pointer. */ 707#define MACH_SEND_NO_BUFFER 0x1000000d 708 /* No message buffer is available. */ 709#define MACH_SEND_TOO_LARGE 0x1000000e 710 /* Send is too large for port */ 711#define MACH_SEND_INVALID_TYPE 0x1000000f 712 /* Invalid msg-type specification. */ 713#define MACH_SEND_INVALID_HEADER 0x10000010 714 /* A field in the header had a bad value. */ 715#define MACH_SEND_INVALID_TRAILER 0x10000011 716 /* The trailer to be sent does not match kernel format. */ 717#define MACH_SEND_INVALID_RT_OOL_SIZE 0x10000015 718 /* compatibility: no longer a returned error */ 719 720#define MACH_RCV_IN_PROGRESS 0x10004001 721 /* Thread is waiting for receive. (Internal use only.) */ 722#define MACH_RCV_INVALID_NAME 0x10004002 723 /* Bogus name for receive port/port-set. */ 724#define MACH_RCV_TIMED_OUT 0x10004003 725 /* Didn't get a message within the timeout value. */ 726#define MACH_RCV_TOO_LARGE 0x10004004 727 /* Message buffer is not large enough for inline data. */ 728#define MACH_RCV_INTERRUPTED 0x10004005 729 /* Software interrupt. */ 730#define MACH_RCV_PORT_CHANGED 0x10004006 731 /* compatibility: no longer a returned error */ 732#define MACH_RCV_INVALID_NOTIFY 0x10004007 733 /* Bogus notify port argument. */ 734#define MACH_RCV_INVALID_DATA 0x10004008 735 /* Bogus message buffer for inline data. */ 736#define MACH_RCV_PORT_DIED 0x10004009 737 /* Port/set was sent away/died during receive. */ 738#define MACH_RCV_IN_SET 0x1000400a 739 /* compatibility: no longer a returned error */ 740#define MACH_RCV_HEADER_ERROR 0x1000400b 741 /* Error receiving message header. See special bits. */ 742#define MACH_RCV_BODY_ERROR 0x1000400c 743 /* Error receiving message body. See special bits. */ 744#define MACH_RCV_INVALID_TYPE 0x1000400d 745 /* Invalid msg-type specification in scatter list. */ 746#define MACH_RCV_SCATTER_SMALL 0x1000400e 747 /* Out-of-line overwrite region is not large enough */ 748#define MACH_RCV_INVALID_TRAILER 0x1000400f 749 /* trailer type or number of trailer elements not supported */ 750#define MACH_RCV_IN_PROGRESS_TIMED 0x10004011 751 /* Waiting for receive with timeout. (Internal use only.) */ 752 753 754__BEGIN_DECLS 755 756/* 757 * Routine: mach_msg_overwrite 758 * Purpose: 759 * Send and/or receive a message. If the message operation 760 * is interrupted, and the user did not request an indication 761 * of that fact, then restart the appropriate parts of the 762 * operation silently (trap version does not restart). 763 * 764 * Distinct send and receive buffers may be specified. If 765 * no separate receive buffer is specified, the msg parameter 766 * will be used for both send and receive operations. 767 * 768 * In addition to a distinct receive buffer, that buffer may 769 * already contain scatter control information to direct the 770 * receiving of the message. 771 */ 772 773extern mach_msg_return_t mach_msg_overwrite( 774 mach_msg_header_t *msg, 775 mach_msg_option_t option, 776 mach_msg_size_t send_size, 777 mach_msg_size_t rcv_size, 778 mach_port_name_t rcv_name, 779 mach_msg_timeout_t timeout, 780 mach_port_name_t notify, 781 mach_msg_header_t *rcv_msg, 782 mach_msg_size_t rcv_limit); 783 784#ifndef KERNEL 785 786/* 787 * Routine: mach_msg 788 * Purpose: 789 * Send and/or receive a message. If the message operation 790 * is interrupted, and the user did not request an indication 791 * of that fact, then restart the appropriate parts of the 792 * operation silently (trap version does not restart). 793 */ 794extern mach_msg_return_t mach_msg( 795 mach_msg_header_t *msg, 796 mach_msg_option_t option, 797 mach_msg_size_t send_size, 798 mach_msg_size_t rcv_size, 799 mach_port_name_t rcv_name, 800 mach_msg_timeout_t timeout, 801 mach_port_name_t notify); 802 803#elif defined(MACH_KERNEL_PRIVATE) 804 805extern mach_msg_return_t mach_msg_receive_results(void); 806 807#endif /* KERNEL */ 808 809__END_DECLS 810 811#endif /* _MACH_MESSAGE_H_ */ 812 813