Merge commit 'origin/silc.1.1.branch'
[silc.git] / lib / silccore / silccommand.h
1 /*
2
3   silccommand.h
4
5   Author: Pekka Riikonen <priikone@silcnet.org>
6
7   Copyright (C) 1997 - 2008 Pekka Riikonen
8
9   This program is free software; you can redistribute it and/or modify
10   it under the terms of the GNU General Public License as published by
11   the Free Software Foundation; version 2 of the License.
12
13   This program is distributed in the hope that it will be useful,
14   but WITHOUT ANY WARRANTY; without even the implied warranty of
15   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16   GNU General Public License for more details.
17
18 */
19
20 /****h* silccore/SILC Command Interface
21  *
22  * DESCRIPTION
23  *
24  * Implementation of the Command Payload. The Command Payload is used to
25  * send commands and also command replies usually between client and
26  * server.
27  *
28  ***/
29
30 #ifndef SILCCOMMAND_H
31 #define SILCCOMMAND_H
32
33 /****s* silccore/SilcCommandAPI/SilcCommandPayload
34  *
35  * NAME
36  *
37  *    typedef struct SilcCommandPayloadStruct *SilcCommandPayload;
38  *
39  * DESCRIPTION
40  *
41  *    This context is the actual Command Payload and is allocated
42  *    by silc_command_payload_parse and given as argument usually to
43  *    all silc_command_payload_* functions.  It is freed by the
44  *    silc_command_payload_free function.
45  *
46  ***/
47 typedef struct SilcCommandPayloadStruct *SilcCommandPayload;
48
49 /****d* silccore/SilcCommandAPI/SilcCommandFlags
50  *
51  * NAME
52  *
53  *    typedef enum { ... } SilcCommandFlags;
54  *
55  * DESCRIPTION
56  *
57  *    Command flags that set how the commands behave on different
58  *    situations. These can be OR'es together to set multiple flags.
59  *    The application is resoponsible of implementing the behaviour
60  *    of these flags. These are here just to define generic flags.
61  *    The server usually makes use of these flags.
62  *
63  * SOURCE
64  */
65 typedef enum {
66   SILC_CF_NONE           = 0,
67
68   /* Command may only be used once per (about) 2 seconds. Bursts up
69      to 5 commands are allowed though. */
70   SILC_CF_LAG            = (1L << 1),
71
72   /* Command may only be used once per (about) 2 seconds. No bursts
73      are allowed at all. */
74   SILC_CF_LAG_STRICT     = (1L << 2),
75
76   /* Command is available for registered connections (connections
77      whose ID has been created. */
78   SILC_CF_REG            = (1L << 3),
79
80   /* Command is available only for server operators */
81   SILC_CF_OPER           = (1L << 4),
82
83   /* Command is available only for SILC (router) operators. If this
84      is set SILC_CF_OPER is not necessary to be set. */
85   SILC_CF_SILC_OPER      = (1L << 5),
86
87 } SilcCommandFlag;
88 /***/
89
90 /****d* silccore/SilcCommandAPI/SilcCommand
91  *
92  * NAME
93  *
94  *    typedef SilcUInt8 SilcCommand;
95  *
96  * DESCRIPTION
97  *
98  *    The SilcCommand type definition and the commands. The commands
99  *    listed here are the official SILC Commands and they have client
100  *    and server counterparts.
101  *
102  * SOURCE
103  */
104 typedef SilcUInt8 SilcCommand;
105
106 /* All SILC commands. These are commands that have client and server
107    counterparts. */
108 #define SILC_COMMAND_NONE               0
109 #define SILC_COMMAND_WHOIS              1
110 #define SILC_COMMAND_WHOWAS             2
111 #define SILC_COMMAND_IDENTIFY           3
112 #define SILC_COMMAND_NICK               4
113 #define SILC_COMMAND_LIST               5
114 #define SILC_COMMAND_TOPIC              6
115 #define SILC_COMMAND_INVITE             7
116 #define SILC_COMMAND_QUIT               8
117 #define SILC_COMMAND_KILL               9
118 #define SILC_COMMAND_INFO               10
119 #define SILC_COMMAND_STATS              11
120 #define SILC_COMMAND_PING               12
121 #define SILC_COMMAND_OPER               13
122 #define SILC_COMMAND_JOIN               14
123 #define SILC_COMMAND_MOTD               15
124 #define SILC_COMMAND_UMODE              16
125 #define SILC_COMMAND_CMODE              17
126 #define SILC_COMMAND_CUMODE             18
127 #define SILC_COMMAND_KICK               19
128 #define SILC_COMMAND_BAN                20
129 #define SILC_COMMAND_DETACH             21
130 #define SILC_COMMAND_WATCH              22
131 #define SILC_COMMAND_SILCOPER           23
132 #define SILC_COMMAND_LEAVE              24
133 #define SILC_COMMAND_USERS              25
134 #define SILC_COMMAND_GETKEY             26
135 #define SILC_COMMAND_SERVICE            27
136
137 /* Private range start */
138 #define SILC_COMMAND_PRIVATE            200
139 #define SILC_COMMAND_PRIV_CONNECT       200
140 #define SILC_COMMAND_PRIV_CLOSE         201
141 #define SILC_COMMAND_PRIV_SHUTDOWN      202
142
143 /* Reserved */
144 #define SILC_COMMAND_RESERVED           255
145 /***/
146
147 /* Prototypes */
148
149 /****f* silccore/SilcCommandAPI/silc_command_payload_parse
150  *
151  * SYNOPSIS
152  *
153  *    SilcCommandPayload
154  *    silc_command_payload_parse(const unsigned char *payload,
155  *                               SilcUInt32 payload_len);
156  *
157  * DESCRIPTION
158  *
159  *    Parses command payload returning new command payload structure. The
160  *    `buffer' is the raw payload.
161  *
162  ***/
163 SilcCommandPayload silc_command_payload_parse(const unsigned char *payload,
164                                               SilcUInt32 payload_len);
165
166 /****f* silccore/SilcCommandAPI/silc_command_payload_encode
167  *
168  * SYNOPSIS
169  *
170  *    SilcBuffer silc_command_payload_encode(SilcCommand cmd,
171  *                                           SilcUInt32 argc,
172  *                                           unsigned char **argv,
173  *                                           SilcUInt32 *argv_lens,
174  *                                           SilcUInt32 *argv_types,
175  *                                           SilcUInt16 ident);
176  *
177  * DESCRIPTION
178  *
179  *     Encodes Command Payload returning it to SilcBuffer.
180  *
181  ***/
182 SilcBuffer silc_command_payload_encode(SilcCommand cmd,
183                                        SilcUInt32 argc,
184                                        unsigned char **argv,
185                                        SilcUInt32 *argv_lens,
186                                        SilcUInt32 *argv_types,
187                                        SilcUInt16 ident);
188
189 /****f* silccore/SilcCommandAPI/silc_command_payload_encode_payload
190  *
191  * SYNOPSIS
192  *
193  *    SilcBuffer
194  *    silc_command_payload_encode_payload(SilcCommandPayload payload);
195  *
196  * DESCRIPTION
197  *
198  *    Same as silc_command_payload_encode but encodes the buffer from
199  *    SilcCommandPayload structure instead of raw data.
200  *
201  ***/
202 SilcBuffer silc_command_payload_encode_payload(SilcCommandPayload payload);
203
204 /****f* silccore/SilcCommandAPI/silc_command_payload_encode_va
205  *
206  * SYNOPSIS
207  *
208  *    SilcBuffer silc_command_payload_encode_va(SilcCommand cmd,
209  *                                              SilcUInt16 ident,
210  *                                              SilcUInt32 argc, ...);
211  *
212  * DESCRIPTION
213  *
214  *    Encodes Command payload with variable argument list. The arguments
215  *    must be: SilcUInt32, unsigned char *, unsigned int, ... One
216  *    {SilcUInt32, unsigned char * and unsigned int} forms one argument,
217  *    thus `argc' in case when sending one {SilcUInt32, unsigned char *
218  *    and SilcUInt32} equals one (1) and when sending two of those it
219  *    equals two (2), and so on. This has to be preserved or bad things
220  *    will happen. The variable arguments is: {type, data, data_len}.
221  *
222  ***/
223 SilcBuffer silc_command_payload_encode_va(SilcCommand cmd,
224                                           SilcUInt16 ident,
225                                           SilcUInt32 argc, ...);
226
227 /****f* silccore/SilcCommandAPI/silc_command_payload_encode_vap
228  *
229  * SYNOPSIS
230  *
231  *    SilcBuffer silc_command_payload_encode_vap(SilcCommand cmd,
232  *                                               SilcUInt16 ident,
233  *                                               SilcUInt32 argc, va_list ap);
234  *
235  * DESCRIPTION
236  *
237  *    This is equivalent to the silc_command_payload_encode_va except
238  *    takes the va_list as argument.
239  *
240  ***/
241 SilcBuffer silc_command_payload_encode_vap(SilcCommand cmd,
242                                            SilcUInt16 ident,
243                                            SilcUInt32 argc, va_list ap);
244
245 /****f* silccore/SilcCommandAPI/silc_command_reply_payload_encode_va
246  *
247  * SYNOPSIS
248  *
249  *    SilcBuffer
250  *    silc_command_reply_payload_encode_va(SilcCommand cmd,
251  *                                         SilcStatus status,
252  *                                         SilcStatus error,
253  *                                         SilcUInt16 ident,
254  *                                         SilcUInt32 argc, ...);
255  *
256  * DESCRIPTION
257  *
258  *    Same as silc_command_payload_encode_va except that this is used to
259  *    encode strictly command reply packets.  The `argc' must not count
260  *    `status' and `error' as arguments.  The `status' includes the
261  *    command reply status.  If single reply will be sent then it includes
262  *    SILC_STATUS_OK if error did not occur.  It includes an error value
263  *    if error did occur.  In this case `error' field is ignored.  If
264  *    there will be multiple successful command replies then the `status'
265  *    includes a list value and `error' is ignored.  If there will
266  *    multiple error replies the `status' includes a list value, and
267  *    the `error' includes an error value.  Thus, the `error' value is
268  *    specified only if there will be list of errors.
269  *
270  * NOTES
271  *
272  *    Protocol defines that it is possible to send both list of successful
273  *    and list of error replies at the same time, as long as the error
274  *    replies are sent after the successful replies.
275  *
276  ***/
277 SilcBuffer
278 silc_command_reply_payload_encode_va(SilcCommand cmd,
279                                      SilcStatus status,
280                                      SilcStatus error,
281                                      SilcUInt16 ident,
282                                      SilcUInt32 argc, ...);
283
284 /****f* silccore/SilcCommandAPI/silc_command_reply_payload_encode_vap
285  *
286  * SYNOPSIS
287  *
288  *    SilcBuffer
289  *    silc_command_reply_payload_encode_vap(SilcCommand cmd,
290  *                                          SilcStatus status,
291  *                                          SilcStatus error,
292  *                                          SilcUInt16 ident, SilcUInt32 argc,
293  *                                          va_list ap);
294  *
295  * DESCRIPTION
296  *
297  *    This is equivalent to the silc_command_reply_payload_encode_va except
298  *    takes the va_list as argument.
299  *
300  ***/
301 SilcBuffer
302 silc_command_reply_payload_encode_vap(SilcCommand cmd,
303                                       SilcStatus status,
304                                       SilcStatus error,
305                                       SilcUInt16 ident, SilcUInt32 argc,
306                                       va_list ap);
307
308 /****f* silccore/SilcCommandAPI/silc_command_free
309  *
310  * SYNOPSIS
311  *
312  *    void silc_command_payload_free(SilcCommandPayload payload);
313  *
314  * DESCRIPTION
315  *
316  *    Frees the Command Payload and all data in it.
317  *
318  ***/
319 void silc_command_payload_free(SilcCommandPayload payload);
320
321 /****f* silccore/SilcCommandAPI/silc_command_get
322  *
323  * SYNOPSIS
324  *
325  *    SilcCommand silc_command_get(SilcCommandPayload payload);
326  *
327  * DESCRIPTION
328  *
329  *    Return the command from the payload.
330  *
331  ***/
332 SilcCommand silc_command_get(SilcCommandPayload payload);
333
334 /****f* silccore/SilcCommandAPI/silc_command_get_args
335  *
336  * SYNOPSIS
337  *
338  *    SilcArgumentPayload silc_command_get_args(SilcCommandPayload payload);
339  *
340  * DESCRIPTION
341  *
342  *    Return the Arguments Payload containing the arguments from the
343  *    Command Payload. The caller must not free it.
344  *
345  ***/
346 SilcArgumentPayload silc_command_get_args(SilcCommandPayload payload);
347
348 /****f* silccore/SilcCommandAPI/silc_command_get_ident
349  *
350  * SYNOPSIS
351  *
352  *    SilcUInt16 silc_command_get_ident(SilcCommandPayload payload);
353  *
354  * DESCRIPTION
355  *
356  *    Return the command identifier from the payload. The identifier can
357  *    be used to identify which command reply belongs to which command.
358  *    The client sets the identifier to the payload and server must return
359  *    the same identifier in the command reply.
360  *
361  ***/
362 SilcUInt16 silc_command_get_ident(SilcCommandPayload payload);
363
364 /****f* silccore/SilcCommandAPI/silc_command_get_status
365  *
366  * SYNOPSIS
367  *
368  *    SilcBool silc_command_get_status(SilcCommandPayload payload,
369  *                                 SilcStatus *status,
370  *                                 SilcStatus *error);
371  *
372  * DESCRIPTION
373  *
374  *    This function returns the command reply status into `status' and
375  *    error status, if error occurred into the `error'.  The function
376  *    returns TRUE if command reply status is not error, and FALSE if
377  *    error occurred.  In this case the `error' will include the actual
378  *    error status.  The `status' can be in this case some list value
379  *    which indicates that there will be list of errors.
380  *
381  ***/
382 SilcBool silc_command_get_status(SilcCommandPayload payload,
383                                  SilcStatus *status,
384                                  SilcStatus *error);
385
386 /****f* silccore/SilcCommandAPI/silc_command_set_ident
387  *
388  * SYNOPSIS
389  *
390  *    void silc_command_set_ident(SilcCommandPayload payload,
391  *                                SilcUInt16 ident);
392  *
393  * DESCRIPTION
394  *
395  *    Function to set identifier to already allocated Command Payload. Command
396  *    payloads are frequentlly resent in SILC and thusly this makes it easy
397  *    to set the identifier without encoding new Command Payload.
398  *
399  ***/
400 void silc_command_set_ident(SilcCommandPayload payload, SilcUInt16 ident);
401
402 /****f* silccore/SilcCommandAPI/silc_command_set_command
403  *
404  * SYNOPSIS
405  *
406  *    void silc_command_set_command(SilcCommandPayload payload,
407  *                                  SilcCommand command);
408  *
409  * DESCRIPTION
410  *
411  *    Function to set the command to already allocated Command Payload. This
412  *    makes it easy to change the command in the payload without encoding new
413  *    Command Payload.
414  *
415  ***/
416 void silc_command_set_command(SilcCommandPayload payload, SilcCommand command);
417
418 #endif