blob: 96e01c82787190823f9cd68c1a584713aa85afe1 [file] [log] [blame]
Willy Tarreaud1d54542012-09-12 22:58:11 +02001/*
2 * Protocol registration functions.
3 *
4 * Copyright 2000-2012 Willy Tarreau <w@1wt.eu>
5 *
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License
8 * as published by the Free Software Foundation; either version
9 * 2 of the License, or (at your option) any later version.
10 *
11 */
12
Willy Tarreaua6e3be72016-08-10 18:24:48 +020013#include <sys/types.h>
Willy Tarreaub550d002015-02-20 16:53:25 +010014#include <sys/socket.h>
15
Willy Tarreaud1d54542012-09-12 22:58:11 +020016#include <common/config.h>
17#include <common/errors.h>
18#include <common/mini-clist.h>
19#include <common/standard.h>
20
21#include <types/protocol.h>
22
23/* List head of all registered protocols */
24static struct list protocols = LIST_HEAD_INIT(protocols);
William Lallemand2d3f8a42018-09-11 16:51:28 +020025struct protocol *__protocol_by_family[AF_CUST_MAX] = { };
Willy Tarreaud1d54542012-09-12 22:58:11 +020026
27/* Registers the protocol <proto> */
28void protocol_register(struct protocol *proto)
29{
30 LIST_ADDQ(&protocols, &proto->list);
William Lallemand2d3f8a42018-09-11 16:51:28 +020031 if (proto->sock_domain >= 0 && proto->sock_domain < AF_CUST_MAX)
Willy Tarreaub550d002015-02-20 16:53:25 +010032 __protocol_by_family[proto->sock_domain] = proto;
Willy Tarreaud1d54542012-09-12 22:58:11 +020033}
34
35/* Unregisters the protocol <proto>. Note that all listeners must have
36 * previously been unbound.
37 */
38void protocol_unregister(struct protocol *proto)
39{
40 LIST_DEL(&proto->list);
41 LIST_INIT(&proto->list);
42}
43
44/* binds all listeners of all registered protocols. Returns a composition
45 * of ERR_NONE, ERR_RETRYABLE, ERR_FATAL.
46 */
47int protocol_bind_all(char *errmsg, int errlen)
48{
49 struct protocol *proto;
50 int err;
51
52 err = 0;
53 list_for_each_entry(proto, &protocols, list) {
54 if (proto->bind_all) {
55 err |= proto->bind_all(proto, errmsg, errlen);
56 if ( err & ERR_ABORT )
57 break;
58 }
59 }
60 return err;
61}
62
63/* unbinds all listeners of all registered protocols. They are also closed.
64 * This must be performed before calling exit() in order to get a chance to
65 * remove file-system based sockets and pipes.
66 * Returns a composition of ERR_NONE, ERR_RETRYABLE, ERR_FATAL, ERR_ABORT.
67 */
68int protocol_unbind_all(void)
69{
70 struct protocol *proto;
71 int err;
72
73 err = 0;
74 list_for_each_entry(proto, &protocols, list) {
75 if (proto->unbind_all) {
76 err |= proto->unbind_all(proto);
77 }
78 }
79 return err;
80}
81
82/* enables all listeners of all registered protocols. This is intended to be
83 * used after a fork() to enable reading on all file descriptors. Returns a
84 * composition of ERR_NONE, ERR_RETRYABLE, ERR_FATAL.
85 */
86int protocol_enable_all(void)
87{
88 struct protocol *proto;
89 int err;
90
91 err = 0;
92 list_for_each_entry(proto, &protocols, list) {
93 if (proto->enable_all) {
94 err |= proto->enable_all(proto);
95 }
96 }
97 return err;
98}
99
100/* disables all listeners of all registered protocols. This may be used before
101 * a fork() to avoid duplicating poll lists. Returns a composition of ERR_NONE,
102 * ERR_RETRYABLE, ERR_FATAL.
103 */
104int protocol_disable_all(void)
105{
106 struct protocol *proto;
107 int err;
108
109 err = 0;
110 list_for_each_entry(proto, &protocols, list) {
111 if (proto->disable_all) {
112 err |= proto->disable_all(proto);
113 }
114 }
115 return err;
116}
117
Willy Tarreaud1d54542012-09-12 22:58:11 +0200118/*
119 * Local variables:
120 * c-indent-level: 8
121 * c-basic-offset: 8
122 * End:
123 */