Annotation of Gnu-Mach/ipc/ipc_notify.c, revision 1.1.1.4

1.1.1.2   root        1: /*
1.1       root        2:  * Mach Operating System
                      3:  * Copyright (c) 1991,1990,1989 Carnegie Mellon University
                      4:  * All Rights Reserved.
1.1.1.2   root        5:  *
1.1       root        6:  * Permission to use, copy, modify and distribute this software and its
                      7:  * documentation is hereby granted, provided that both the copyright
                      8:  * notice and this permission notice appear in all copies of the
                      9:  * software, derivative works or modified versions, and any portions
                     10:  * thereof, and that both notices appear in supporting documentation.
1.1.1.2   root       11:  *
1.1       root       12:  * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS"
                     13:  * CONDITION.  CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
                     14:  * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
1.1.1.2   root       15:  *
1.1       root       16:  * Carnegie Mellon requests users of this software to return to
1.1.1.2   root       17:  *
1.1       root       18:  *  Software Distribution Coordinator  or  [email protected]
                     19:  *  School of Computer Science
                     20:  *  Carnegie Mellon University
                     21:  *  Pittsburgh PA 15213-3890
1.1.1.2   root       22:  *
1.1       root       23:  * any improvements or extensions that they make and grant Carnegie Mellon
                     24:  * the rights to redistribute these changes.
                     25:  */
                     26: /*
                     27:  *     File:   ipc/ipc_notify.c
                     28:  *     Author: Rich Draves
                     29:  *     Date:   1989
                     30:  *
                     31:  *     Notification-sending functions.
                     32:  */
                     33: 
1.1.1.3   root       34: #include <kern/printf.h>
1.1       root       35: #include <mach/port.h>
                     36: #include <mach/message.h>
                     37: #include <mach/notify.h>
                     38: #include <kern/assert.h>
                     39: #include <ipc/ipc_kmsg.h>
                     40: #include <ipc/ipc_mqueue.h>
                     41: #include <ipc/ipc_notify.h>
                     42: #include <ipc/ipc_port.h>
                     43: 
                     44: #include <ipc/ipc_machdep.h>
                     45: 
                     46: mach_port_deleted_notification_t       ipc_notify_port_deleted_template;
                     47: mach_msg_accepted_notification_t       ipc_notify_msg_accepted_template;
                     48: mach_port_destroyed_notification_t     ipc_notify_port_destroyed_template;
                     49: mach_no_senders_notification_t         ipc_notify_no_senders_template;
                     50: mach_send_once_notification_t          ipc_notify_send_once_template;
                     51: mach_dead_name_notification_t          ipc_notify_dead_name_template;
                     52: 
                     53: #define NOTIFY_MSGH_SEQNO      0
                     54: 
                     55: /*
                     56:  *     Routine:        ipc_notify_init_port_deleted
                     57:  *     Purpose:
                     58:  *             Initialize a template for port-deleted notifications.
                     59:  */
                     60: 
                     61: void
1.1.1.4 ! root       62: ipc_notify_init_port_deleted(mach_port_deleted_notification_t *n)
1.1       root       63: {
                     64:        mach_msg_header_t *m = &n->not_header;
                     65:        mach_msg_type_t *t = &n->not_type;
                     66: 
                     67:        m->msgh_bits = MACH_MSGH_BITS(MACH_MSG_TYPE_PORT_SEND_ONCE, 0);
                     68:        m->msgh_size = sizeof *n;
                     69:        m->msgh_seqno = NOTIFY_MSGH_SEQNO;
                     70:        m->msgh_local_port = MACH_PORT_NULL;
                     71:        m->msgh_remote_port = MACH_PORT_NULL;
                     72:        m->msgh_id = MACH_NOTIFY_PORT_DELETED;
                     73: 
                     74:        t->msgt_name = MACH_MSG_TYPE_PORT_NAME;
                     75:        t->msgt_size = PORT_T_SIZE_IN_BITS;
                     76:        t->msgt_number = 1;
                     77:        t->msgt_inline = TRUE;
                     78:        t->msgt_longform = FALSE;
                     79:        t->msgt_deallocate = FALSE;
                     80:        t->msgt_unused = 0;
                     81: 
                     82:        n->not_port = MACH_PORT_NULL;
                     83: }
                     84: 
                     85: /*
                     86:  *     Routine:        ipc_notify_init_msg_accepted
                     87:  *     Purpose:
                     88:  *             Initialize a template for msg-accepted notifications.
                     89:  */
                     90: 
                     91: void
1.1.1.4 ! root       92: ipc_notify_init_msg_accepted(mach_msg_accepted_notification_t *n)
1.1       root       93: {
                     94:        mach_msg_header_t *m = &n->not_header;
                     95:        mach_msg_type_t *t = &n->not_type;
                     96: 
                     97:        m->msgh_bits = MACH_MSGH_BITS(MACH_MSG_TYPE_PORT_SEND_ONCE, 0);
                     98:        m->msgh_size = sizeof *n;
                     99:        m->msgh_seqno = NOTIFY_MSGH_SEQNO;
                    100:        m->msgh_local_port = MACH_PORT_NULL;
                    101:        m->msgh_remote_port = MACH_PORT_NULL;
                    102:        m->msgh_id = MACH_NOTIFY_MSG_ACCEPTED;
                    103: 
                    104:        t->msgt_name = MACH_MSG_TYPE_PORT_NAME;
                    105:        t->msgt_size = PORT_T_SIZE_IN_BITS;
                    106:        t->msgt_number = 1;
                    107:        t->msgt_inline = TRUE;
                    108:        t->msgt_longform = FALSE;
                    109:        t->msgt_deallocate = FALSE;
                    110:        t->msgt_unused = 0;
                    111: 
                    112:        n->not_port = MACH_PORT_NULL;
                    113: }
                    114: 
                    115: /*
                    116:  *     Routine:        ipc_notify_init_port_destroyed
                    117:  *     Purpose:
                    118:  *             Initialize a template for port-destroyed notifications.
                    119:  */
                    120: 
                    121: void
1.1.1.4 ! root      122: ipc_notify_init_port_destroyed(mach_port_destroyed_notification_t *n)
1.1       root      123: {
                    124:        mach_msg_header_t *m = &n->not_header;
                    125:        mach_msg_type_t *t = &n->not_type;
                    126: 
                    127:        m->msgh_bits = MACH_MSGH_BITS_COMPLEX |
                    128:                MACH_MSGH_BITS(MACH_MSG_TYPE_PORT_SEND_ONCE, 0);
                    129:        m->msgh_size = sizeof *n;
                    130:        m->msgh_seqno = NOTIFY_MSGH_SEQNO;
                    131:        m->msgh_local_port = MACH_PORT_NULL;
                    132:        m->msgh_remote_port = MACH_PORT_NULL;
                    133:        m->msgh_id = MACH_NOTIFY_PORT_DESTROYED;
                    134: 
                    135:        t->msgt_name = MACH_MSG_TYPE_PORT_RECEIVE;
                    136:        t->msgt_size = PORT_T_SIZE_IN_BITS;
                    137:        t->msgt_number = 1;
                    138:        t->msgt_inline = TRUE;
                    139:        t->msgt_longform = FALSE;
                    140:        t->msgt_deallocate = FALSE;
                    141:        t->msgt_unused = 0;
                    142: 
                    143:        n->not_port = MACH_PORT_NULL;
                    144: }
                    145: 
                    146: /*
                    147:  *     Routine:        ipc_notify_init_no_senders
                    148:  *     Purpose:
                    149:  *             Initialize a template for no-senders notifications.
                    150:  */
                    151: 
                    152: void
                    153: ipc_notify_init_no_senders(
                    154:        mach_no_senders_notification_t  *n)
                    155: {
                    156:        mach_msg_header_t *m = &n->not_header;
                    157:        mach_msg_type_t *t = &n->not_type;
                    158: 
                    159:        m->msgh_bits = MACH_MSGH_BITS(MACH_MSG_TYPE_PORT_SEND_ONCE, 0);
                    160:        m->msgh_size = sizeof *n;
                    161:        m->msgh_seqno = NOTIFY_MSGH_SEQNO;
                    162:        m->msgh_local_port = MACH_PORT_NULL;
                    163:        m->msgh_remote_port = MACH_PORT_NULL;
                    164:        m->msgh_id = MACH_NOTIFY_NO_SENDERS;
                    165: 
                    166:        t->msgt_name = MACH_MSG_TYPE_INTEGER_32;
                    167:        t->msgt_size = PORT_T_SIZE_IN_BITS;
                    168:        t->msgt_number = 1;
                    169:        t->msgt_inline = TRUE;
                    170:        t->msgt_longform = FALSE;
                    171:        t->msgt_deallocate = FALSE;
                    172:        t->msgt_unused = 0;
                    173: 
                    174:        n->not_count = 0;
                    175: }
                    176: 
                    177: /*
                    178:  *     Routine:        ipc_notify_init_send_once
                    179:  *     Purpose:
                    180:  *             Initialize a template for send-once notifications.
                    181:  */
                    182: 
                    183: void
                    184: ipc_notify_init_send_once(
                    185:        mach_send_once_notification_t   *n)
                    186: {
                    187:        mach_msg_header_t *m = &n->not_header;
                    188: 
                    189:        m->msgh_bits = MACH_MSGH_BITS(MACH_MSG_TYPE_PORT_SEND_ONCE, 0);
                    190:        m->msgh_size = sizeof *n;
                    191:        m->msgh_seqno = NOTIFY_MSGH_SEQNO;
                    192:        m->msgh_local_port = MACH_PORT_NULL;
                    193:        m->msgh_remote_port = MACH_PORT_NULL;
                    194:        m->msgh_id = MACH_NOTIFY_SEND_ONCE;
                    195: }
                    196: 
                    197: /*
                    198:  *     Routine:        ipc_notify_init_dead_name
                    199:  *     Purpose:
                    200:  *             Initialize a template for dead-name notifications.
                    201:  */
                    202: 
                    203: void
                    204: ipc_notify_init_dead_name(
                    205:        mach_dead_name_notification_t   *n)
                    206: {
                    207:        mach_msg_header_t *m = &n->not_header;
                    208:        mach_msg_type_t *t = &n->not_type;
                    209: 
                    210:        m->msgh_bits = MACH_MSGH_BITS(MACH_MSG_TYPE_PORT_SEND_ONCE, 0);
                    211:        m->msgh_size = sizeof *n;
                    212:        m->msgh_seqno = NOTIFY_MSGH_SEQNO;
                    213:        m->msgh_local_port = MACH_PORT_NULL;
                    214:        m->msgh_remote_port = MACH_PORT_NULL;
                    215:        m->msgh_id = MACH_NOTIFY_DEAD_NAME;
                    216: 
                    217:        t->msgt_name = MACH_MSG_TYPE_PORT_NAME;
                    218:        t->msgt_size = PORT_T_SIZE_IN_BITS;
                    219:        t->msgt_number = 1;
                    220:        t->msgt_inline = TRUE;
                    221:        t->msgt_longform = FALSE;
                    222:        t->msgt_deallocate = FALSE;
                    223:        t->msgt_unused = 0;
                    224: 
                    225:        n->not_port = MACH_PORT_NULL;
                    226: }
                    227: 
                    228: /*
                    229:  *     Routine:        ipc_notify_init
                    230:  *     Purpose:
                    231:  *             Initialize the notification subsystem.
                    232:  */
                    233: 
                    234: void
                    235: ipc_notify_init(void)
                    236: {
                    237:        ipc_notify_init_port_deleted(&ipc_notify_port_deleted_template);
                    238:        ipc_notify_init_msg_accepted(&ipc_notify_msg_accepted_template);
                    239:        ipc_notify_init_port_destroyed(&ipc_notify_port_destroyed_template);
                    240:        ipc_notify_init_no_senders(&ipc_notify_no_senders_template);
                    241:        ipc_notify_init_send_once(&ipc_notify_send_once_template);
                    242:        ipc_notify_init_dead_name(&ipc_notify_dead_name_template);
                    243: }
                    244: 
                    245: /*
                    246:  *     Routine:        ipc_notify_port_deleted
                    247:  *     Purpose:
                    248:  *             Send a port-deleted notification.
                    249:  *     Conditions:
                    250:  *             Nothing locked.
                    251:  *             Consumes a ref/soright for port.
                    252:  */
                    253: 
                    254: void
1.1.1.4 ! root      255: ipc_notify_port_deleted(
        !           256:        ipc_port_t      port,
        !           257:        mach_port_t     name)
1.1       root      258: {
                    259:        ipc_kmsg_t kmsg;
                    260:        mach_port_deleted_notification_t *n;
                    261: 
                    262:        kmsg = ikm_alloc(sizeof *n);
                    263:        if (kmsg == IKM_NULL) {
1.1.1.3   root      264:                printf("dropped port-deleted (0x%p, 0x%lx)\n", port, name);
1.1       root      265:                ipc_port_release_sonce(port);
                    266:                return;
                    267:        }
                    268: 
                    269:        ikm_init(kmsg, sizeof *n);
                    270:        n = (mach_port_deleted_notification_t *) &kmsg->ikm_header;
                    271:        *n = ipc_notify_port_deleted_template;
                    272: 
                    273:        n->not_header.msgh_remote_port = (mach_port_t) port;
                    274:        n->not_port = name;
                    275: 
                    276:        ipc_mqueue_send_always(kmsg);
                    277: }
                    278: 
                    279: /*
                    280:  *     Routine:        ipc_notify_msg_accepted
                    281:  *     Purpose:
                    282:  *             Send a msg-accepted notification.
                    283:  *     Conditions:
                    284:  *             Nothing locked.
                    285:  *             Consumes a ref/soright for port.
                    286:  */
                    287: 
                    288: void
1.1.1.4 ! root      289: ipc_notify_msg_accepted(
        !           290:        ipc_port_t      port,
        !           291:        mach_port_t     name)
1.1       root      292: {
                    293:        ipc_kmsg_t kmsg;
                    294:        mach_msg_accepted_notification_t *n;
                    295: 
                    296:        kmsg = ikm_alloc(sizeof *n);
                    297:        if (kmsg == IKM_NULL) {
1.1.1.3   root      298:                printf("dropped msg-accepted (0x%p, 0x%lx)\n", port, name);
1.1       root      299:                ipc_port_release_sonce(port);
                    300:                return;
                    301:        }
                    302: 
                    303:        ikm_init(kmsg, sizeof *n);
                    304:        n = (mach_msg_accepted_notification_t *) &kmsg->ikm_header;
                    305:        *n = ipc_notify_msg_accepted_template;
                    306: 
                    307:        n->not_header.msgh_remote_port = (mach_port_t) port;
                    308:        n->not_port = name;
                    309: 
                    310:        ipc_mqueue_send_always(kmsg);
                    311: }
                    312: 
                    313: /*
                    314:  *     Routine:        ipc_notify_port_destroyed
                    315:  *     Purpose:
                    316:  *             Send a port-destroyed notification.
                    317:  *     Conditions:
                    318:  *             Nothing locked.
                    319:  *             Consumes a ref/soright for port.
                    320:  *             Consumes a ref for right, which should be a receive right
                    321:  *             prepped for placement into a message.  (In-transit,
                    322:  *             or in-limbo if a circularity was detected.)
                    323:  */
                    324: 
                    325: void
1.1.1.4 ! root      326: ipc_notify_port_destroyed(
        !           327:        ipc_port_t      port,
        !           328:        ipc_port_t      right)
1.1       root      329: {
                    330:        ipc_kmsg_t kmsg;
                    331:        mach_port_destroyed_notification_t *n;
                    332: 
                    333:        kmsg = ikm_alloc(sizeof *n);
                    334:        if (kmsg == IKM_NULL) {
1.1.1.3   root      335:                printf("dropped port-destroyed (0x%p, 0x%p)\n",
1.1       root      336:                       port, right);
                    337:                ipc_port_release_sonce(port);
                    338:                ipc_port_release_receive(right);
                    339:                return;
                    340:        }
                    341: 
                    342:        ikm_init(kmsg, sizeof *n);
                    343:        n = (mach_port_destroyed_notification_t *) &kmsg->ikm_header;
                    344:        *n = ipc_notify_port_destroyed_template;
                    345: 
                    346:        n->not_header.msgh_remote_port = (mach_port_t) port;
                    347:        n->not_port = (mach_port_t) right;
                    348: 
                    349:        ipc_mqueue_send_always(kmsg);
                    350: }
                    351: 
                    352: /*
                    353:  *     Routine:        ipc_notify_no_senders
                    354:  *     Purpose:
                    355:  *             Send a no-senders notification.
                    356:  *     Conditions:
                    357:  *             Nothing locked.
                    358:  *             Consumes a ref/soright for port.
                    359:  */
                    360: 
                    361: void
1.1.1.4 ! root      362: ipc_notify_no_senders(
        !           363:        ipc_port_t              port,
        !           364:        mach_port_mscount_t     mscount)
1.1       root      365: {
                    366:        ipc_kmsg_t kmsg;
                    367:        mach_no_senders_notification_t *n;
                    368: 
                    369:        kmsg = ikm_alloc(sizeof *n);
                    370:        if (kmsg == IKM_NULL) {
1.1.1.3   root      371:                printf("dropped no-senders (0x%p, %u)\n", port, mscount);
1.1       root      372:                ipc_port_release_sonce(port);
                    373:                return;
                    374:        }
                    375: 
                    376:        ikm_init(kmsg, sizeof *n);
                    377:        n = (mach_no_senders_notification_t *) &kmsg->ikm_header;
                    378:        *n = ipc_notify_no_senders_template;
                    379: 
                    380:        n->not_header.msgh_remote_port = (mach_port_t) port;
                    381:        n->not_count = mscount;
                    382: 
                    383:        ipc_mqueue_send_always(kmsg);
                    384: }
                    385: 
                    386: /*
                    387:  *     Routine:        ipc_notify_send_once
                    388:  *     Purpose:
                    389:  *             Send a send-once notification.
                    390:  *     Conditions:
                    391:  *             Nothing locked.
                    392:  *             Consumes a ref/soright for port.
                    393:  */
                    394: 
                    395: void
1.1.1.4 ! root      396: ipc_notify_send_once(ipc_port_t port)
1.1       root      397: {
                    398:        ipc_kmsg_t kmsg;
                    399:        mach_send_once_notification_t *n;
                    400: 
                    401:        kmsg = ikm_alloc(sizeof *n);
                    402:        if (kmsg == IKM_NULL) {
1.1.1.3   root      403:                printf("dropped send-once (0x%p)\n", port);
1.1       root      404:                ipc_port_release_sonce(port);
                    405:                return;
                    406:        }
                    407: 
                    408:        ikm_init(kmsg, sizeof *n);
                    409:        n = (mach_send_once_notification_t *) &kmsg->ikm_header;
                    410:        *n = ipc_notify_send_once_template;
                    411: 
                    412:        n->not_header.msgh_remote_port = (mach_port_t) port;
                    413: 
                    414:        ipc_mqueue_send_always(kmsg);
                    415: }
                    416: 
                    417: /*
                    418:  *     Routine:        ipc_notify_dead_name
                    419:  *     Purpose:
                    420:  *             Send a dead-name notification.
                    421:  *     Conditions:
                    422:  *             Nothing locked.
                    423:  *             Consumes a ref/soright for port.
                    424:  */
                    425: 
                    426: void
1.1.1.4 ! root      427: ipc_notify_dead_name(
        !           428:        ipc_port_t      port,
        !           429:        mach_port_t     name)
1.1       root      430: {
                    431:        ipc_kmsg_t kmsg;
                    432:        mach_dead_name_notification_t *n;
                    433: 
                    434:        kmsg = ikm_alloc(sizeof *n);
                    435:        if (kmsg == IKM_NULL) {
1.1.1.3   root      436:                printf("dropped dead-name (0x%p, 0x%lx)\n", port, name);
1.1       root      437:                ipc_port_release_sonce(port);
                    438:                return;
                    439:        }
                    440: 
                    441:        ikm_init(kmsg, sizeof *n);
                    442:        n = (mach_dead_name_notification_t *) &kmsg->ikm_header;
                    443:        *n = ipc_notify_dead_name_template;
                    444: 
                    445:        n->not_header.msgh_remote_port = (mach_port_t) port;
                    446:        n->not_port = name;
                    447: 
                    448:        ipc_mqueue_send_always(kmsg);
                    449: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.