8322 nl: misleading-indentation
[unleashed/tickless.git] / usr / src / common / svc / repcache_protocol.h
blob07504a467e7375e7f9e16bb5ea0176a5d53a9a17
1 /*
2 * CDDL HEADER START
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
19 * CDDL HEADER END
23 * Copyright (c) 2004, 2010, Oracle and/or its affiliates. All rights reserved.
24 * Copyright (c) 2016 by Delphix. All rights reserved.
27 #ifndef _REPCACHE_PROTOCOL_H
28 #define _REPCACHE_PROTOCOL_H
31 * The Repository Cache Protocol
32 * -----------------------------
34 * 1. Introduction
35 * ---------------
36 * This header file defines the private protocols between libscf(3lib) and
37 * svc.configd(1m). There are two separate protocols:
39 * 1. The 'global' protocol, accessible via an fattach(3C)ed door located
40 * at REPOSITORY_DOOR_NAME.
42 * 2. The 'client' protocol, accessible through a door created using the
43 * global protocol, which allows access to the repository.
45 * 1.1 Design restrictions
46 * -----------------------
47 * A basic constraint of the door IPC mechanism is that there is no reliable
48 * delivery. In particular:
50 * 1. If libscf(3lib) recieves an EINTR from door_call(), it doesn't know
51 * whether or not the server recieved (and is processing) its request.
53 * 2. When svc.configd(1M) calls door_return(), the client may have already
54 * received an EINTR, aborting its door_call(). In this case, the
55 * returned values are dropped on the floor.
57 * The practical upshot of all of this is simple:
59 * Every individual protocol action must be idempotent.
61 * That is, a client must be able to retry any single request multiple times,
62 * and get the correct results.
64 * 1.2. Protocol shorthand
65 * -----------------------
66 * We represent by "REQUEST(arg1, arg2) -> result, res1, [desc]" a request code
67 * of REP_PROTOCOL_REQUEST (or REPOSITORY_DOOR_REQUEST), which takes two
68 * additional arguments, arg1 and arg2, and returns a result code, res1, and
69 * a file descriptor desc.
71 * If an error occurs, the server will usually only send the result code. (a
72 * short return)
74 * Inside the protocol destription, <foo> indicates the type foo indicates.
76 * 2. The Global protocol
77 * ----------------------
78 * Everything starting with "REPOSITORY_DOOR" or "repository_door" belongs
79 * to the global protocol.
81 * 2.1. Global requests
82 * --------------------
84 * REQUEST_CONNECT(rdr_flags, ...) -> result, [new_door]
85 * Request a new Client door. rdr_flags determines attributes of the
86 * connection:
88 * FLAG_DEBUG
89 * Sets connection debugging flags to those in rdr_debug.
91 * The new door is returned with DOOR_RELEASE set, so if the client does
92 * not recieve the response, the new door will recieve an unref
93 * notification. This makes this request idempotent.
95 * 2.2. Global reponse codes
96 * -------------------------
97 * GLXXX: This needs to be thought through.
99 * SUCCESS
100 * FAIL_BAD_REQUEST
101 * FAIL_VERSION_MISMATCH
102 * FAIL_BAD_FLAG
103 * FAIL_BAD_USER
104 * FAIL_NO_RESOURCES
106 * 3. The Client protocol
107 * ----------------------
108 * Everything starting with "REP_PROTOCOL" or "rep_protocol" belongs to the
109 * client protocol.
111 * 3.1. Techniques used
112 * --------------------
113 * 3.1.1. Client-controlled identifiers
115 * An idiom the protocol uses to lower the number of round trips is
116 * client-controlled identifiers. The basic idea is this: whenever a
117 * client wants to set up and use a piece of server state, it picks an
118 * integer *which it knows is not in use* to identify it. The server then
119 * maintains per-client, per-resource id->resource maps. This has a number
120 * of advantages:
122 * 1. Since the client allocates the identifiers, we don't need to do
123 * a round-trip just to allocate a number.
125 * 2. Since it is the client's job to make sure identifiers don't collide,
126 * idempotency for setup (destroy) are simple: If the identifier
127 * already exists (does not exist), we just return success.
129 * 3. Since the identifiers are per-client, the design automatically
130 * precludes clients being able to manipulate other client's state.
132 * 3.1.2 Sequence numbers
134 * A standard way of gaining idempotency is introducing sequence numbers.
135 * These are simply integers which get incremented at points in the protocol,
136 * and make sure the client and server are in sync.
138 * In this protocol, we use sequence numbers for requests (like ITER_READ)
139 * which are repeated, returning different data each time. Since requests
140 * can also be repeated due to unreliable dispatch, the client increments
141 * the sequence number after every successful request. This allows the server
142 * to differentiate the two cases. (note that this means that failing
143 * requests have no side effects and are repeatable)
145 * 3.2. Client abstractions
146 * ------------------------
147 * 3.2.1 Entities
149 * An "entity" is a typed register which the client can manipulate.
150 * Entities are named in the protocol by client-controlled identifiers.
151 * They have a fixed type for their entire lifetime, and may be in one
152 * of two states:
154 * valid
155 * The entity has a valid value, and may be read from. This state
156 * is reached by a successful write to the entity by some protocol
157 * step.
159 * invalid
160 * The entity does not contain a valid value. There are a number
161 * of ways to reach this state:
163 * 1. The entity was just created.
164 * 2. The underlying object that this entity refers to was destroyed.
165 * 3. A protocol request which would have modified this entity
166 * failed.
168 * An entity is an element in the tree of repository data. Every entity
169 * (except for the most distant SCOPE) has exactly one parent. Entities
170 * can have multiple children of different types, restricted by its base
171 * type.
173 * The ENTITY_GET call is used to get the root of the tree (the most local
174 * scope)
176 * 3.2.2. The entity tree
177 * ----------------------
178 * The structure of a scope is as follows:
180 * _______
181 * | SCOPE |
182 * |_______|
183 * \ .
184 * \ .
185 * \_________
186 * | SERVICE |
187 * |_________|
188 * /. \ .
189 * /. \ .
190 * ____/ \__________
191 * | PG | | INSTANCE |
192 * |____| |__________|
193 * /. \ .
194 * /. \ .
195 * ____/ \__________
196 * | PG | | SNAPSHOT |
197 * |____| |__________|
198 * \ .
199 * \ .
200 * \___________
201 * | SNAPLEVEL |
202 * |___________|
203 * /.
204 * /.
205 * ____/
206 * | PG |
207 * |____|
209 * Where the dots indicate an arbitrary number (including 0) of children.
211 * For a given scope, the next scope (in the sense of distance) is its
212 * TYPE_SCOPE parent. The furthest out scope has no parent.
214 * 3.2.2 Iterators
216 * GLXXX
218 * 3.3. Client requests
219 * --------------------
221 * CLOSE() -> result
222 * Closes the connection, revoking the door. After this call completes,
223 * no further calls will succeed.
225 * ENTITY_SETUP(entity_id, type) -> result
226 * Sets up an entity, identified by entity_id, to identify a single
227 * <type>. <type> may not be TYPE_NONE.
229 * ENTITY_NAME(entity_id, name_type) -> result, name
230 * Returns the name of entity_id. name_type determines which type of
231 * name to get.
233 * ENTITY_PARENT_TYPE(entity_id) -> result, parent_type
234 * Retrieves the type of entity_id's parent
236 * ENTITY_GET_CHILD(entity_id, child_id, name) -> result
237 * Puts entity_id's child (of child_id's type) named 'name' into child_id.
239 * ENTITY_GET_PARENT(entity_id, out_id) -> result
240 * Puts entity_id's parent into out_id.
242 * ENTITY_GET(entity_id, number) -> result
243 * Makes entity_id point to a particular object. If any error
244 * occurs, dest_id will be invalid.
246 * ENTITY_UPDATE(entity_id, changeid) -> result
247 * Updates the entity to pick up any new changes.
249 * ENTITY_CREATE_CHILD(entity_id, type, name, child_id, changeid) -> result
250 * Attaches the object of type /type/ in child_id as the child of
251 * entity_id named 'name'.
253 * ENTITY_CREATE_PG(entity_id, name, type, flags, child_id, changeid) -> result
254 * Creates a property group child of entity_id named 'name', type 'type'
255 * and flags 'flags', and puts the resulting object in child_id.
257 * ENTITY_DELETE(entity_id, changeid) -> result
258 * Deletes the entity represented by entity_id.
260 * ENTITY_RESET(entity_id) -> result
261 * Resets the entity.
263 * ENTITY_TEARDOWN(entity_id) -> result
264 * Destroys the entity entity_id.
266 * ITER_SETUP(iter_id) -> result
267 * Sets up an iterator id.
269 * ITER_START(iter_id, entity_id, itertype, flags, pattern) -> result
270 * Sets up an iterator, identified by iter_id, which will iterate the
271 * <itertype> children of entity_id whose names match 'pattern',
272 * with the matching controlled by flags. Initializing an iterator
273 * counts as the first sequence number (1).
275 * ITER_READ(iter_id, sequence, entity_id) -> result
276 * Retrieves the next element of iterator iter_id. Sequence starts at 2,
277 * and is incremented by the client after each successful iteration.
278 * The result is written to entity_id, which must be of the same type
279 * as the iterator result. The iterator must not be iterating values.
281 * ITER_READ_VALUE(iter_id, sequence) -> result, type, value
282 * Retrieves the next value for iterator iter_id. Sequence starts at 2,
283 * and is incremented by the client after each successful iteration.
284 * The iterator must be iterating a property's values.
286 * ITER_RESET(iter_id) -> result
287 * Throws away any accumulated state.
289 * ITER_TEARDOWN(iter_id) -> result
290 * Destroys the iterator iter_id.
292 * NEXT_SNAPLEVEL(entity_src, entity_dst) -> result
293 * If entity_src is a snapshot, set entity_dst to the first snaplevel
294 * in it. If entity_src is a snaplevel, set entity_dst to the next
295 * snaplevel, or fail if there isn't one.
297 * SNAPSHOT_TAKE(entity_id, name, dest_id, flags) -> result
298 * Takes a snapshot of entity_id, creating snaplevels for the instance and
299 * its parent service. If flags is REP_SNAPSHOT_NEW, a new snapshot named
300 * 'name' is created as a child of entity_id, dest_id is pointed to it,
301 * and the new snaplevels are attached to it. If flags is
302 * REP_SNAPSHOT_ATTACH, name must be empty, and the new snaplevels are
303 * attached to the snapshot dest_id points to.
305 * SNAPSHOT_TAKE_NAMED(entity_id, instname, svcname, name, dest_id) -> result
306 * Like SNAPSHOT_TAKE, but always acts as if REP_SNAPSHOT_NEW is
307 * specified, and instname and svcname override the actual service and
308 * instance names, respectively, written into the snaplevels.
310 * Note that this is only useful for writing snapshots which will later
311 * be transferred to another instance (svc:/svcname:instname/)
313 * SNAPSHOT_ATTACH(source_id, dest_id) -> result
314 * The snaplevels attached to the snapshot referenced by source_id are
315 * attached to the snapshot dest_id is pointed at.
317 * PROPERTY_GET_TYPE(entity_id) -> result, value type
318 * Finds the value type of entity_id, which must be a property.
320 * PROPERTY_GET_VALUE(entity_id) -> result, type, value
321 * If the property contains a single value, returns it and its type.
323 * PROPERTYGRP_SETUP_WAIT(entity_id) -> result, [pipe fd]
324 * Sets up a notification for changes to the object entity_id currently
325 * references. On success, returns one side of a pipe -- when there
326 * has been a change (or the daemon dies), the other end of the pipe will
327 * be closed.
329 * Only one of these can be set up per client -- attempts to set up more
330 * than one will cause the previous one to get closed.
332 * PROPERTYGRP_TX_START(entity_id_tx, entity_id) -> result
333 * Makes entity_id_tx point to the same property group as entity_id,
334 * then attempts to set up entity_id_tx as a transaction on that group.
335 * entity_id and entity_id_tx must be distinct. On failure, entity_id_tx
336 * is reset.
338 * PROPERTYGRP_TX_COMMIT(entity_id, data) -> result
339 * Gives the actual steps to follow, and attempts to commit them.
341 * CLIENT_ADD_NOTIFY(type, pattern) -> result
342 * Adds a new property group name or type pattern to the notify list
343 * (see CLIENT_WAIT). If successful, takes effect immediately.
345 * CLIENT_WAIT(entity_id) -> result, fmri
346 * Waits for a change to a propertygroup that matches the patterns
347 * set up using CLIENT_ADD_NOTIFY, and puts the resultant propertygroup
348 * in entity_id. Note that if an error occurs, you can loose
349 * notifications. Either entity_id is set to a changed propertygroup,
350 * or fmri is a non-zero-length string identifying a deleted thing.
352 * BACKUP(name) -> result
353 * Backs up the persistant repository with a particular name.
355 * SET_ANNOTATION(operation, file)
356 * Set up a security audit annotation event. operation is the name of
357 * the operation that is being annotated, and file is the file being
358 * processed. This will be used to mark operations which comprise
359 * multiple primitive operations such as svccfg import.
361 * SWITCH(flag) -> result
362 * The flag is used to indicate the direction of the switch operation.
363 * When the flag is set to 'fast', move the main repository from the
364 * default location (/etc/svc) to the tmpfs locationa (/etc/svc/volatile).
365 * When it is set to 'perm', the switch is reversed.
368 #include <door.h>
369 #include <stddef.h>
370 #include <sys/sysmacros.h>
372 #ifdef __cplusplus
373 extern "C" {
374 #endif
377 * svc.configd initial protocol details
379 #define REPOSITORY_DOOR_BASEVER (('R' << 24) | ('e' << 16) | ('p' << 8))
380 #define REPOSITORY_DOOR_NAME "/etc/svc/volatile/repository_door"
381 #define REPOSITORY_DOOR_COOKIE ((void *)REPOSITORY_DOOR_BASEVER)
383 #define REPOSITORY_BOOT_BACKUP ((const char *)"boot")
386 * This value should be incremented any time the protocol changes. When in
387 * doubt, bump it.
389 #define REPOSITORY_DOOR_VERSION (21 + REPOSITORY_DOOR_BASEVER)
392 * flags for rdr_flags
394 #define REPOSITORY_DOOR_FLAG_DEBUG 0x00000001 /* rdr_debug */
396 #define REPOSITORY_DOOR_FLAG_ALL 0x00000001 /* all flags */
399 * Request IDs
401 enum repository_door_requestid {
402 REPOSITORY_DOOR_REQUEST_CONNECT = (('M' << 8) | 1)
405 enum repository_door_statusid {
406 REPOSITORY_DOOR_SUCCESS = 0,
407 REPOSITORY_DOOR_FAIL_BAD_REQUEST = 1,
408 REPOSITORY_DOOR_FAIL_VERSION_MISMATCH = 2,
409 REPOSITORY_DOOR_FAIL_BAD_FLAG = 3,
410 REPOSITORY_DOOR_FAIL_NO_RESOURCES = 4,
411 REPOSITORY_DOOR_FAIL_PERMISSION_DENIED = 5
415 * You may only add elements to the end of this structure.
417 typedef struct repository_door_request {
418 uint32_t rdr_version; /* must be first element */
419 enum repository_door_requestid rdr_request;
420 uint32_t rdr_flags;
421 uint32_t rdr_debug;
422 } repository_door_request_t;
424 typedef struct repository_door_response {
425 enum repository_door_statusid rdr_status;
426 } repository_door_response_t;
429 * Client interface. Used on doors returned by REQUEST_CONNECT
432 #define REP_PROTOCOL_NAME_LEN 120 /* maximum name length */
433 #define REP_PROTOCOL_VALUE_LEN 4096 /* maximum value length */
435 #define REP_PROTOCOL_FMRI_LEN (6 * REP_PROTOCOL_NAME_LEN)
437 #define REP_PROTOCOL_BASE ('C' << 8)
440 * Request codes
442 enum rep_protocol_requestid {
443 REP_PROTOCOL_CLOSE = REP_PROTOCOL_BASE,
445 REP_PROTOCOL_ENTITY_SETUP,
446 REP_PROTOCOL_ENTITY_NAME,
447 REP_PROTOCOL_ENTITY_PARENT_TYPE,
448 REP_PROTOCOL_ENTITY_GET_CHILD,
449 REP_PROTOCOL_ENTITY_GET_PARENT,
450 REP_PROTOCOL_ENTITY_GET,
451 REP_PROTOCOL_ENTITY_UPDATE,
452 REP_PROTOCOL_ENTITY_CREATE_CHILD,
453 REP_PROTOCOL_ENTITY_CREATE_PG,
454 REP_PROTOCOL_ENTITY_DELETE,
455 REP_PROTOCOL_ENTITY_RESET,
456 REP_PROTOCOL_ENTITY_TEARDOWN,
458 REP_PROTOCOL_ITER_SETUP,
459 REP_PROTOCOL_ITER_START,
460 REP_PROTOCOL_ITER_READ,
461 REP_PROTOCOL_ITER_READ_VALUE,
462 REP_PROTOCOL_ITER_RESET,
463 REP_PROTOCOL_ITER_TEARDOWN,
465 REP_PROTOCOL_NEXT_SNAPLEVEL,
467 REP_PROTOCOL_SNAPSHOT_TAKE,
468 REP_PROTOCOL_SNAPSHOT_TAKE_NAMED,
469 REP_PROTOCOL_SNAPSHOT_ATTACH,
471 REP_PROTOCOL_PROPERTY_GET_TYPE,
472 REP_PROTOCOL_PROPERTY_GET_VALUE,
474 REP_PROTOCOL_PROPERTYGRP_SETUP_WAIT,
475 REP_PROTOCOL_PROPERTYGRP_TX_START,
476 REP_PROTOCOL_PROPERTYGRP_TX_COMMIT,
478 REP_PROTOCOL_CLIENT_ADD_NOTIFY,
479 REP_PROTOCOL_CLIENT_WAIT,
481 REP_PROTOCOL_BACKUP,
483 REP_PROTOCOL_SET_AUDIT_ANNOTATION,
485 REP_PROTOCOL_SWITCH,
487 REP_PROTOCOL_MAX_REQUEST
491 * Response codes. These are returned to the client, and the errors are
492 * translated into scf_error_t's by libscf (see proto_error()).
494 typedef int32_t rep_protocol_responseid_t;
495 enum rep_protocol_responseid {
496 REP_PROTOCOL_SUCCESS = 0,
497 /* iterators: No more values. */
498 REP_PROTOCOL_DONE = 1,
500 /* Request from client was malformed. */
501 REP_PROTOCOL_FAIL_BAD_REQUEST = -1,
502 /* Prerequisite call has not been made. */
503 REP_PROTOCOL_FAIL_MISORDERED = -2,
504 /* Register for ID has not been created. */
505 REP_PROTOCOL_FAIL_UNKNOWN_ID = -3,
506 /* Out of memory or other resource. */
507 REP_PROTOCOL_FAIL_NO_RESOURCES = -4,
508 /* Type argument is invalid. */
509 REP_PROTOCOL_FAIL_INVALID_TYPE = -5,
510 /* Requested object does not exist. */
511 REP_PROTOCOL_FAIL_NOT_FOUND = -6,
512 /* Register for given ID does not point to an object. */
513 REP_PROTOCOL_FAIL_NOT_SET = -7,
515 /* Requested name is longer than supplied buffer. */
516 REP_PROTOCOL_FAIL_TRUNCATED = -8,
517 /* Operation requires different type. */
518 REP_PROTOCOL_FAIL_TYPE_MISMATCH = -9,
520 /* Changeable object has been changed since last update. */
521 REP_PROTOCOL_FAIL_NOT_LATEST = -10,
522 /* Creation failed because object with given name exists. */
523 REP_PROTOCOL_FAIL_EXISTS = -11,
524 /* Transaction is invalid. */
525 REP_PROTOCOL_FAIL_BAD_TX = -12,
526 /* Operation is not applicable to indicated object. */
527 REP_PROTOCOL_FAIL_NOT_APPLICABLE = -13,
528 /* Two IDs for operation were unexpectedly equal. */
529 REP_PROTOCOL_FAIL_DUPLICATE_ID = -14,
531 /* Permission denied. */
532 REP_PROTOCOL_FAIL_PERMISSION_DENIED = -15,
533 /* Backend does not exist or otherwise refused access. */
534 REP_PROTOCOL_FAIL_BACKEND_ACCESS = -16,
535 /* Backend is read-only. */
536 REP_PROTOCOL_FAIL_BACKEND_READONLY = -17,
538 /* Object has been deleted. */
539 REP_PROTOCOL_FAIL_DELETED = -18,
541 REP_PROTOCOL_FAIL_UNKNOWN = -0xfd
545 * Types
547 typedef enum rep_protocol_entity {
548 REP_PROTOCOL_ENTITY_NONE,
549 REP_PROTOCOL_ENTITY_SCOPE,
550 REP_PROTOCOL_ENTITY_SERVICE,
551 REP_PROTOCOL_ENTITY_INSTANCE,
552 REP_PROTOCOL_ENTITY_SNAPSHOT,
553 REP_PROTOCOL_ENTITY_SNAPLEVEL,
554 REP_PROTOCOL_ENTITY_PROPERTYGRP,
555 REP_PROTOCOL_ENTITY_CPROPERTYGRP, /* "composed" property group */
556 REP_PROTOCOL_ENTITY_PROPERTY,
557 REP_PROTOCOL_ENTITY_VALUE,
559 REP_PROTOCOL_ENTITY_MAX
560 } rep_protocol_entity_t;
562 typedef enum rep_protocol_value_type {
563 REP_PROTOCOL_TYPE_INVALID = '\0',
564 REP_PROTOCOL_TYPE_BOOLEAN = 'b',
565 REP_PROTOCOL_TYPE_COUNT = 'c',
566 REP_PROTOCOL_TYPE_INTEGER = 'i',
567 REP_PROTOCOL_TYPE_TIME = 't',
568 REP_PROTOCOL_TYPE_STRING = 's',
569 REP_PROTOCOL_TYPE_OPAQUE = 'o',
571 REP_PROTOCOL_SUBTYPE_USTRING = REP_PROTOCOL_TYPE_STRING|('u' << 8),
572 REP_PROTOCOL_SUBTYPE_URI = REP_PROTOCOL_TYPE_STRING|('U' << 8),
573 REP_PROTOCOL_SUBTYPE_FMRI = REP_PROTOCOL_TYPE_STRING|('f' << 8),
575 REP_PROTOCOL_SUBTYPE_HOST = REP_PROTOCOL_TYPE_STRING|('h' << 8),
576 REP_PROTOCOL_SUBTYPE_HOSTNAME = REP_PROTOCOL_TYPE_STRING|('N' << 8),
577 REP_PROTOCOL_SUBTYPE_NETADDR = REP_PROTOCOL_TYPE_STRING|('n' << 8),
578 REP_PROTOCOL_SUBTYPE_NETADDR_V4 = REP_PROTOCOL_TYPE_STRING|('4' << 8),
579 REP_PROTOCOL_SUBTYPE_NETADDR_V6 = REP_PROTOCOL_TYPE_STRING|('6' << 8)
580 } rep_protocol_value_type_t;
583 #define REP_PROTOCOL_BASE_TYPE(t) ((t) & 0x00ff)
584 #define REP_PROTOCOL_SUBTYPE(t) (((t) & 0xff00) >> 8)
587 * Request structures
589 typedef struct rep_protocol_request {
590 enum rep_protocol_requestid rpr_request;
591 } rep_protocol_request_t;
593 struct rep_protocol_iter_request {
594 enum rep_protocol_requestid rpr_request;
595 uint32_t rpr_iterid;
598 struct rep_protocol_iter_start {
599 enum rep_protocol_requestid rpr_request; /* ITER_START */
600 uint32_t rpr_iterid;
602 uint32_t rpr_entity;
603 uint32_t rpr_itertype;
604 uint32_t rpr_flags;
605 char rpr_pattern[REP_PROTOCOL_NAME_LEN];
607 #define RP_ITER_START_ALL 0x00000001 /* ignore pattern, match all */
608 #define RP_ITER_START_EXACT 0x00000002 /* exact match with pattern */
609 #define RP_ITER_START_PGTYPE 0x00000003 /* exact match pg type */
610 #define RP_ITER_START_FILT_MASK 0x00000003
611 #define RP_ITER_START_COMPOSED 0x00000004 /* composed */
613 struct rep_protocol_iter_read {
614 enum rep_protocol_requestid rpr_request; /* ITER_READ */
615 uint32_t rpr_iterid;
616 uint32_t rpr_sequence; /* client increments upon success */
617 uint32_t rpr_entityid; /* entity to write result to */
620 struct rep_protocol_iter_read_value {
621 enum rep_protocol_requestid rpr_request; /* ITER_READ_VALUE */
622 uint32_t rpr_iterid;
623 uint32_t rpr_sequence; /* client increments upon success */
626 struct rep_protocol_entity_setup {
627 enum rep_protocol_requestid rpr_request; /* ENTITY_SETUP */
628 uint32_t rpr_entityid;
629 uint32_t rpr_entitytype;
632 struct rep_protocol_entity_name {
633 enum rep_protocol_requestid rpr_request; /* ENTITY_NAME */
634 uint32_t rpr_entityid;
635 uint32_t rpr_answertype;
637 #define RP_ENTITY_NAME_NAME 0
638 #define RP_ENTITY_NAME_PGTYPE 1
639 #define RP_ENTITY_NAME_PGFLAGS 2
640 #define RP_ENTITY_NAME_SNAPLEVEL_SCOPE 3
641 #define RP_ENTITY_NAME_SNAPLEVEL_SERVICE 4
642 #define RP_ENTITY_NAME_SNAPLEVEL_INSTANCE 5
643 #define RP_ENTITY_NAME_PGREADPROT 6
645 struct rep_protocol_entity_update {
646 enum rep_protocol_requestid rpr_request; /* ENTITY_UPDATE */
647 uint32_t rpr_entityid;
648 uint32_t rpr_changeid;
651 struct rep_protocol_entity_parent_type {
652 enum rep_protocol_requestid rpr_request; /* ENTITY_PARENT_TYPE */
653 uint32_t rpr_entityid;
656 struct rep_protocol_entity_parent {
657 enum rep_protocol_requestid rpr_request; /* ENTITY_GET_PARENT */
658 uint32_t rpr_entityid;
659 uint32_t rpr_outid;
662 struct rep_protocol_entity_get {
663 enum rep_protocol_requestid rpr_request; /* ENTITY_SET */
664 uint32_t rpr_entityid;
665 uint32_t rpr_object;
667 #define RP_ENTITY_GET_INVALIDATE 1
668 #define RP_ENTITY_GET_MOST_LOCAL_SCOPE 2
670 struct rep_protocol_entity_create_child {
671 enum rep_protocol_requestid rpr_request; /* ENTITY_CREATE_CHILD */
672 uint32_t rpr_entityid;
673 uint32_t rpr_childtype;
674 uint32_t rpr_childid;
675 uint32_t rpr_changeid;
676 char rpr_name[REP_PROTOCOL_NAME_LEN];
679 struct rep_protocol_entity_create_pg {
680 enum rep_protocol_requestid rpr_request; /* ENTITY_CREATE_PG */
681 uint32_t rpr_entityid;
682 uint32_t rpr_childtype;
683 uint32_t rpr_childid;
684 uint32_t rpr_changeid;
685 char rpr_name[REP_PROTOCOL_NAME_LEN];
686 char rpr_type[REP_PROTOCOL_NAME_LEN];
687 uint32_t rpr_flags;
690 struct rep_protocol_entity_get_child {
691 enum rep_protocol_requestid rpr_request; /* ENTITY_GET_CHILD */
692 uint32_t rpr_entityid;
693 uint32_t rpr_childid;
694 char rpr_name[REP_PROTOCOL_NAME_LEN];
697 struct rep_protocol_entity_delete {
698 enum rep_protocol_requestid rpr_request; /* ENTITY_DELETE_CHILD */
699 uint32_t rpr_entityid;
700 uint32_t rpr_changeid;
703 struct rep_protocol_entity_reset {
704 enum rep_protocol_requestid rpr_request; /* ENTITY_NAME */
705 uint32_t rpr_entityid;
708 struct rep_protocol_entity_request {
709 enum rep_protocol_requestid rpr_request; /* ENTITY_NAME */
710 uint32_t rpr_entityid;
713 struct rep_protocol_entity_teardown {
714 enum rep_protocol_requestid rpr_request; /* ENTITY_TEARDOWN */
715 uint32_t rpr_entityid;
718 struct rep_protocol_entity_pair {
719 enum rep_protocol_requestid rpr_request; /* NEXT_SNAPLEVEL */
720 uint32_t rpr_entity_src;
721 uint32_t rpr_entity_dst;
724 struct rep_protocol_transaction_start {
725 enum rep_protocol_requestid rpr_request; /* TX_SETUP */
726 uint32_t rpr_entityid_tx; /* property group tx entity */
727 uint32_t rpr_entityid; /* property group entity */
730 struct rep_protocol_transaction_commit {
731 enum rep_protocol_requestid rpr_request; /* TX_COMMIT */
732 uint32_t rpr_entityid;
733 uint32_t rpr_size; /* size of entire structure */
734 uint8_t rpr_cmd[1];
737 #define REP_PROTOCOL_TRANSACTION_COMMIT_SIZE(sz) \
738 (offsetof(struct rep_protocol_transaction_commit, rpr_cmd[sz]))
740 #define REP_PROTOCOL_TRANSACTION_COMMIT_MIN_SIZE \
741 REP_PROTOCOL_TRANSACTION_COMMIT_SIZE(0)
743 enum rep_protocol_transaction_action {
744 REP_PROTOCOL_TX_ENTRY_INVALID, /* N/A */
745 REP_PROTOCOL_TX_ENTRY_NEW, /* new property */
746 REP_PROTOCOL_TX_ENTRY_CLEAR, /* clear old property */
747 REP_PROTOCOL_TX_ENTRY_REPLACE, /* change type of old property */
748 REP_PROTOCOL_TX_ENTRY_DELETE /* delete property (no values) */
751 struct rep_protocol_transaction_cmd {
752 enum rep_protocol_transaction_action rptc_action;
753 uint32_t rptc_type;
754 uint32_t rptc_size; /* size of entire structure */
755 uint32_t rptc_name_len;
756 uint8_t rptc_data[1];
759 #define REP_PROTOCOL_TRANSACTION_CMD_SIZE(sz) \
760 (offsetof(struct rep_protocol_transaction_cmd, rptc_data[sz]))
762 #define REP_PROTOCOL_TRANSACTION_CMD_MIN_SIZE \
763 REP_PROTOCOL_TRANSACTION_CMD_SIZE(0)
765 #define TX_SIZE(x) P2ROUNDUP((x), sizeof (uint32_t))
767 struct rep_protocol_transaction_request {
768 enum rep_protocol_requestid rpr_request; /* SETUP, ABORT or TEARDOWN */
769 uint32_t rpr_txid;
772 struct rep_protocol_property_request {
773 enum rep_protocol_requestid rpr_request;
774 uint32_t rpr_entityid;
777 struct rep_protocol_propertygrp_request {
778 enum rep_protocol_requestid rpr_request;
779 uint32_t rpr_entityid;
782 struct rep_protocol_notify_request {
783 enum rep_protocol_requestid rpr_request;
784 uint32_t rpr_type;
785 char rpr_pattern[REP_PROTOCOL_NAME_LEN];
787 #define REP_PROTOCOL_NOTIFY_PGNAME 1
788 #define REP_PROTOCOL_NOTIFY_PGTYPE 2
790 struct rep_protocol_wait_request {
791 enum rep_protocol_requestid rpr_request;
792 uint32_t rpr_entityid;
795 struct rep_protocol_snapshot_take {
796 enum rep_protocol_requestid rpr_request; /* SNAPSHOT_TAKE */
797 uint32_t rpr_entityid_src;
798 uint32_t rpr_entityid_dest;
799 int rpr_flags;
800 char rpr_name[REP_PROTOCOL_NAME_LEN];
802 #define REP_SNAPSHOT_NEW 0x00000001
803 #define REP_SNAPSHOT_ATTACH 0x00000002
805 struct rep_protocol_snapshot_take_named {
806 enum rep_protocol_requestid rpr_request; /* SNAPSHOT_TAKE_NAMED */
807 uint32_t rpr_entityid_src;
808 uint32_t rpr_entityid_dest;
809 char rpr_svcname[REP_PROTOCOL_NAME_LEN];
810 char rpr_instname[REP_PROTOCOL_NAME_LEN];
811 char rpr_name[REP_PROTOCOL_NAME_LEN];
814 struct rep_protocol_snapshot_attach {
815 enum rep_protocol_requestid rpr_request; /* SNAPSHOT_ATTACH */
816 uint32_t rpr_entityid_src;
817 uint32_t rpr_entityid_dest;
820 struct rep_protocol_backup_request {
821 enum rep_protocol_requestid rpr_request; /* BACKUP */
822 uint32_t rpr_changeid;
823 char rpr_name[REP_PROTOCOL_NAME_LEN];
826 struct rep_protocol_annotation {
827 enum rep_protocol_requestid rpr_request; /* SET_ANNOTATION */
828 char rpr_operation[REP_PROTOCOL_NAME_LEN];
829 char rpr_file[MAXPATHLEN];
832 struct rep_protocol_switch_request {
833 enum rep_protocol_requestid rpr_request; /* SWITCH */
834 uint32_t rpr_changeid;
835 int rpr_flag;
839 * Response structures
841 typedef struct rep_protocol_response {
842 rep_protocol_responseid_t rpr_response;
843 } rep_protocol_response_t;
845 struct rep_protocol_integer_response {
846 rep_protocol_responseid_t rpr_response;
847 uint32_t rpr_value;
850 struct rep_protocol_name_response { /* response to ENTITY_NAME */
851 rep_protocol_responseid_t rpr_response;
852 char rpr_name[REP_PROTOCOL_NAME_LEN];
855 struct rep_protocol_fmri_response {
856 rep_protocol_responseid_t rpr_response;
857 char rpr_fmri[REP_PROTOCOL_FMRI_LEN];
860 struct rep_protocol_value_response {
861 rep_protocol_responseid_t rpr_response;
862 rep_protocol_value_type_t rpr_type;
863 char rpr_value[2 * REP_PROTOCOL_VALUE_LEN + 1];
866 #ifdef __cplusplus
868 #endif
870 #endif /* _REPCACHE_PROTOCOL_H */