]> rtime.felk.cvut.cz Git - frescor/fna.git/blob - src_frescan/frescan_bandwidth_reservation.c
update the names and add acceptor thread id to the general data
[frescor/fna.git] / src_frescan / frescan_bandwidth_reservation.c
1 /*!
2  * @file frescan_bandwidth_reservation.c
3  *
4  * @brief FRESCAN bandwidth reservation layer
5  *
6  * This module contains function to negotiate contracts and get the
7  * corresponding frescan sporadic servers.
8  *
9  * @version 0.01
10  *
11  * @date 1-Apr-2008
12  *
13  * @author Daniel Sangorrin <daniel.sangorrin@unican.es>
14  *
15  */
16
17 #include "frescan_bandwidth_reservation.h"
18 #include "frescan_data.h"
19 #include "frescan_requests_queue.h"    // frescan_requests_init
20 #include "frescan_debug.h"
21 #include "frescan_config.h"
22 #include "frescan_servers.h"
23 #include "frescan_negotiation_messages.h"
24 #include "frescan_negotiation_threads.h"
25
26 /**
27  * frescan_bwres_init()
28  *
29  * Init the frescan bandwidth reservation layer
30  */
31
32 int frescan_bwres_init(frescan_network_t net)
33 {
34         int ret;
35         frescan_server_params_t params;
36
37         // TODO: server params must be configurable
38         params.values.budget = 5;
39         params.values.period.tv_sec = 1;
40         params.values.period.tv_nsec = 0;
41         params.prio = FRESCAN_BWRES_NEG_MESSAGES_PRIO;
42
43         ret = frescan_servers_create(net, &params,
44                                      &the_networks[net].neg_messages_ss_id);
45         if (ret != 0) {
46                 ERROR("could not create server for negotiation messages\n");
47                 return ret;
48         }
49
50         ret = frescan_requests_init(FRESCAN_REQUESTS_MX_CEILING);
51         if (ret != 0) {
52                 ERROR("could not initialize the requests\n");
53                 return ret;
54         }
55
56         if (the_networks[net].local_node == FRESCAN_NEG_MASTER_NODE) {
57                 DEBUG(FRESCAN_BWRES_ENABLE_DEBUG, "i am master node (%u)\n",
58                       the_networks[net].local_node);
59                 ret = frescan_master_neg_thread_create(net);
60                 if (ret != 0) {
61                         ERROR("could not initialize the negotiator thread\n");
62                         return ret;
63                 }
64         } else {
65                 DEBUG(FRESCAN_BWRES_ENABLE_DEBUG, "i am a slave node (%u)\n",
66                       the_networks[net].local_node);
67         }
68
69         ret = frescan_acceptor_thread_create(net);
70         if (ret != 0) {
71                 ERROR("could not create acceptor thread\n");
72                 return ret;
73         }
74
75         return 0;
76 }
77
78 /**
79  * frescan_bwres_negotiate()
80  *
81  * negotiate a contract. For that we allocate a reply object and then
82  * we enqueue our request in the master's requests queue (which can be
83  * local or require a network message)
84  */
85
86 int frescan_bwres_negotiate(frescan_network_t net,
87                             const frescan_contract_t *contract,
88                             frescan_ss_t *id)
89 {
90         int ret;
91         frescan_robj_id_t reply;
92         frescan_request_id_t request;
93         frescan_neg_return_info_t return_info;
94         uint8_t msg[200];
95         int size;
96         frescan_send_params_t params;
97
98         ret = frescan_replyobject_alloc(&reply, FRESCAN_BWRES_MX_PRIO);
99         if (ret != 0) {
100                 ERROR("could not allocate reply object\n");
101                 return ret;
102         }
103
104         ret = frescan_request_alloc(&request);
105         if (ret != 0) {
106                 ERROR("could not allocate request\n");
107                 return ret;
108         }
109
110         ret = frescan_request_set_return_info(request,
111                                               (void *) &return_info);
112         if (ret != 0) {
113                 ERROR("could not set return_info pointer\n");
114                 return ret;
115         }
116
117         ret = frescan_request_set_reply(request, reply);
118         if (ret != 0) {
119                 ERROR("could not set reply\n");
120                 return ret;
121         }
122
123         if (the_networks[net].local_node == FRESCAN_NEG_MASTER_NODE) {
124                 DEBUG(FRESCAN_BWRES_ENABLE_DEBUG,
125                       "I am master, negotiation in local node\n");
126
127                 DEBUG(FRESCAN_BWRES_ENABLE_DEBUG,
128                       "set FRESCAN_NEGOTIATE type: %d\n", FRESCAN_NEGOTIATE);
129
130                 ret = frescan_request_set_type(request, FRESCAN_NEGOTIATE);
131                 if (ret != 0) {
132                         ERROR("could not set type\n");
133                         return ret;
134                 }
135
136                 ret = frescan_request_set_contract(request, contract);
137                 if (ret != 0) {
138                         ERROR("could not set contract\n");
139                         return ret;
140                 }
141
142                 ret = frescan_request_set_src(request, FRESCAN_NEG_MASTER_NODE);
143                 if (ret != 0) {
144                         ERROR("could not set src\n");
145                         return ret;
146                 }
147
148                 ret = frescan_requestqueue_enqueue(request);
149                 if (ret != 0) {
150                         ERROR("could not enqueue the request\n");
151                         return ret;
152                 }
153         } else {
154                 DEBUG(FRESCAN_BWRES_ENABLE_DEBUG,
155                       "I am slave, negotiation in master node\n");
156
157                 size = frescan_neg_message_create(msg, request, contract);
158
159                 DEBUG(FRESCAN_BWRES_ENABLE_DEBUG,
160                       "created a neg message, size: %d\n", size);
161
162                 params.net = net;
163                 params.to  = FRESCAN_NEG_MASTER_NODE;
164                 params.channel = FRESCAN_NEG_CHANNEL;
165
166 //                 params.flags = FRESCAN_FP | FRESCAN_ASYNC;
167 //                 params.prio = 8;
168                 params.flags = FRESCAN_SS | FRESCAN_ASYNC;
169                 params.ss = the_networks[net].neg_messages_ss_id;
170
171                 DEBUG(FRESCAN_BWRES_ENABLE_DEBUG,
172                       "send msg to master, net:%u to:%u ss:%u\n",
173                       params.net, params.to, params.ss);
174
175                 ret = frescan_send(&params, msg, size);
176                 if (ret != 0) {
177                         ERROR("error while sending neg request to master\n");
178                         return ret;
179                 }
180         }
181
182         DEBUG(FRESCAN_BWRES_ENABLE_DEBUG, "wait on reply object\n");
183
184         ret = frescan_replyobject_wait(reply);
185         if (ret != 0) {
186                 ERROR("error while waiting on the reply object\n");
187                 return ret;
188         }
189
190         ret = frescan_replyobject_free(reply);
191         if (ret != 0) {
192                 ERROR("could not free reply object\n");
193                 return ret;
194         }
195
196         if (return_info.error) {
197                 DEBUG(FRESCAN_BWRES_ENABLE_DEBUG,
198                       "negotiation was not accepted, error:%d\n",
199                       return_info.error);
200         } else {
201                 DEBUG(FRESCAN_BWRES_ENABLE_DEBUG,
202                       "negotiation finished succesfully ss:%d\n",
203                       return_info.id);
204         }
205
206         *id = return_info.id;
207
208         ret = frescan_request_free(request);
209         if (ret != 0) {
210                 ERROR("could not free request\n");
211                 return ret;
212         }
213
214         return return_info.error;
215 }