1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
|
/*
* include/vservices/protocol/core.h
*
* Copyright (c) 2012-2018 General Dynamics
* Copyright (c) 2014 Open Kernel Labs, Inc.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* These are the common generated definitions for the core protocol drivers;
* specifically the message IDs and the protocol state representation.
*
* This is currently hand-generated, but will eventually be autogenerated,
* from the protocol specifications in core.vs. Please keep it consistent
* with that file.
*/
#define VSERVICE_CORE_PROTOCOL_NAME "com.ok-labs.core"
#define VSERVICE_CORE_PARAM_SIZE_SERVICE_INFO__PROTOCOL_NAME 32
#define VSERVICE_CORE_PARAM_SIZE_SERVICE_INFO__SERVICE_NAME 16
/*
* Identifiers for in-band messages.
*
* This definition applies in both directions, because there is no practical
* limit on message IDs (services are unlikely to define 2^16 distinct message
* names).
*/
typedef enum {
/** simple_protocol core **/
/* message out startup */
VSERVICE_CORE_MSG_STARTUP,
/* message out shutdown */
VSERVICE_CORE_MSG_SHUTDOWN,
/* command in sync connect */
VSERVICE_CORE_REQ_CONNECT,
VSERVICE_CORE_ACK_CONNECT,
VSERVICE_CORE_NACK_CONNECT,
/* command in sync disconnect */
VSERVICE_CORE_REQ_DISCONNECT,
VSERVICE_CORE_ACK_DISCONNECT,
VSERVICE_CORE_NACK_DISCONNECT,
/* command in service_count */
VSERVICE_CORE_REQ_SERVICE_COUNT,
VSERVICE_CORE_ACK_SERVICE_COUNT,
VSERVICE_CORE_NACK_SERVICE_COUNT,
/* command in queued service_info */
VSERVICE_CORE_REQ_SERVICE_INFO,
VSERVICE_CORE_ACK_SERVICE_INFO,
VSERVICE_CORE_NACK_SERVICE_INFO,
/* message inout service_reset */
VSERVICE_CORE_MSG_SERVICE_RESET,
/* message inout service_ready */
VSERVICE_CORE_MSG_SERVICE_READY,
/* message out notification bits */
VSERVICE_CORE_MSG_NOTIFICATION_BITS_INFO,
} vservice_core_message_id_t;
/*
* Notification bits are defined separately for each direction because there
* is relatively limited space to allocate them from (specifically, the bits in
* a machine word). It is unlikely but possible for a protocol to reach this
* limit.
*/
/* Bits in the in (client -> server) notification bitmask. */
typedef enum {
/** simple_protocol core **/
/* No in notifications */
VSERVICE_CORE_NBIT_IN__COUNT = 0,
} vservice_core_nbit_in_t;
/* Masks for the in notification bits */
/* No in notifications */
/* Bits in the out (server -> client) notification bitmask. */
typedef enum {
/** simple_protocol core **/
/* notification out reenumerate */
VSERVICE_CORE_NBIT_OUT_REENUMERATE = 0,
VSERVICE_CORE_NBIT_OUT__COUNT,
} vservice_core_nbit_out_t;
/* Masks for the out notification bits */
#define VSERVICE_CORE_NMASK_OUT_REENUMERATE \
(1 << VSERVICE_CORE_NBIT_OUT_REENUMERATE)
/* Valid states of the interface's generated state machine. */
typedef enum {
/* state offline */
VSERVICE_CORE_STATE_OFFLINE = 0,
/* state disconnected */
VSERVICE_CORE_STATE_DISCONNECTED,
VSERVICE_CORE_STATE_DISCONNECTED__CONNECT,
/* state connected */
VSERVICE_CORE_STATE_CONNECTED,
VSERVICE_CORE_STATE_CONNECTED__DISCONNECT,
/* reset offline */
VSERVICE_CORE_STATE__RESET = VSERVICE_CORE_STATE_OFFLINE,
} vservice_core_statenum_t;
typedef struct {
vservice_core_statenum_t statenum;
bool pending_service_count;
unsigned pending_service_info;
} vservice_core_state_t;
#define VSERVICE_CORE_RESET_STATE (vservice_core_state_t) { \
.statenum = VSERVICE_CORE_STATE__RESET, \
.pending_service_count = false, \
.pending_service_info = 0 }
#define VSERVICE_CORE_STATE_IS_OFFLINE(state) ( \
((state).statenum == VSERVICE_CORE_STATE_OFFLINE))
#define VSERVICE_CORE_STATE_IS_DISCONNECTED(state) ( \
((state).statenum == VSERVICE_CORE_STATE_DISCONNECTED) || \
((state).statenum == VSERVICE_CORE_STATE_DISCONNECTED__CONNECT))
#define VSERVICE_CORE_STATE_IS_CONNECTED(state) ( \
((state).statenum == VSERVICE_CORE_STATE_CONNECTED) || \
((state).statenum == VSERVICE_CORE_STATE_CONNECTED__DISCONNECT))
#define VSERVICE_CORE_STATE_VALID(state) \
VSERVICE_CORE_STATE_IS_OFFLINE(state) ? ( \
((state).pending_service_count == false) && \
((state).pending_service_info == 0)) : \
VSERVICE_CORE_STATE_IS_DISCONNECTED(state) ? ( \
((state).pending_service_count == false) && \
((state).pending_service_info == 0)) : \
VSERVICE_CORE_STATE_IS_CONNECTED(state) ? true : \
false)
|