diff options
Diffstat (limited to 'net/tipc/config.c')
| -rw-r--r-- | net/tipc/config.c | 107 |
1 files changed, 3 insertions, 104 deletions
diff --git a/net/tipc/config.c b/net/tipc/config.c index e6d721692ae0..4b981c053823 100644 --- a/net/tipc/config.c +++ b/net/tipc/config.c | |||
| @@ -43,13 +43,11 @@ | |||
| 43 | #define REPLY_TRUNCATED "<truncated>\n" | 43 | #define REPLY_TRUNCATED "<truncated>\n" |
| 44 | 44 | ||
| 45 | static DEFINE_MUTEX(config_mutex); | 45 | static DEFINE_MUTEX(config_mutex); |
| 46 | static struct tipc_server cfgsrv; | ||
| 47 | 46 | ||
| 48 | static const void *req_tlv_area; /* request message TLV area */ | 47 | static const void *req_tlv_area; /* request message TLV area */ |
| 49 | static int req_tlv_space; /* request message TLV area size */ | 48 | static int req_tlv_space; /* request message TLV area size */ |
| 50 | static int rep_headroom; /* reply message headroom to use */ | 49 | static int rep_headroom; /* reply message headroom to use */ |
| 51 | 50 | ||
| 52 | |||
| 53 | struct sk_buff *tipc_cfg_reply_alloc(int payload_size) | 51 | struct sk_buff *tipc_cfg_reply_alloc(int payload_size) |
| 54 | { | 52 | { |
| 55 | struct sk_buff *buf; | 53 | struct sk_buff *buf; |
| @@ -185,18 +183,6 @@ static struct sk_buff *cfg_set_own_addr(void) | |||
| 185 | return tipc_cfg_reply_none(); | 183 | return tipc_cfg_reply_none(); |
| 186 | } | 184 | } |
| 187 | 185 | ||
| 188 | static struct sk_buff *cfg_set_remote_mng(void) | ||
| 189 | { | ||
| 190 | u32 value; | ||
| 191 | |||
| 192 | if (!TLV_CHECK(req_tlv_area, req_tlv_space, TIPC_TLV_UNSIGNED)) | ||
| 193 | return tipc_cfg_reply_error_string(TIPC_CFG_TLV_ERROR); | ||
| 194 | |||
| 195 | value = ntohl(*(__be32 *)TLV_DATA(req_tlv_area)); | ||
| 196 | tipc_remote_management = (value != 0); | ||
| 197 | return tipc_cfg_reply_none(); | ||
| 198 | } | ||
| 199 | |||
| 200 | static struct sk_buff *cfg_set_max_ports(void) | 186 | static struct sk_buff *cfg_set_max_ports(void) |
| 201 | { | 187 | { |
| 202 | u32 value; | 188 | u32 value; |
| @@ -247,21 +233,10 @@ struct sk_buff *tipc_cfg_do_cmd(u32 orig_node, u16 cmd, const void *request_area | |||
| 247 | /* Check command authorization */ | 233 | /* Check command authorization */ |
| 248 | if (likely(in_own_node(orig_node))) { | 234 | if (likely(in_own_node(orig_node))) { |
| 249 | /* command is permitted */ | 235 | /* command is permitted */ |
| 250 | } else if (cmd >= 0x8000) { | 236 | } else { |
| 251 | rep_tlv_buf = tipc_cfg_reply_error_string(TIPC_CFG_NOT_SUPPORTED | 237 | rep_tlv_buf = tipc_cfg_reply_error_string(TIPC_CFG_NOT_SUPPORTED |
| 252 | " (cannot be done remotely)"); | 238 | " (cannot be done remotely)"); |
| 253 | goto exit; | 239 | goto exit; |
| 254 | } else if (!tipc_remote_management) { | ||
| 255 | rep_tlv_buf = tipc_cfg_reply_error_string(TIPC_CFG_NO_REMOTE); | ||
| 256 | goto exit; | ||
| 257 | } else if (cmd >= 0x4000) { | ||
| 258 | u32 domain = 0; | ||
| 259 | |||
| 260 | if ((tipc_nametbl_translate(TIPC_ZM_SRV, 0, &domain) == 0) || | ||
| 261 | (domain != orig_node)) { | ||
| 262 | rep_tlv_buf = tipc_cfg_reply_error_string(TIPC_CFG_NOT_ZONE_MSTR); | ||
| 263 | goto exit; | ||
| 264 | } | ||
| 265 | } | 240 | } |
| 266 | 241 | ||
| 267 | /* Call appropriate processing routine */ | 242 | /* Call appropriate processing routine */ |
| @@ -310,18 +285,12 @@ struct sk_buff *tipc_cfg_do_cmd(u32 orig_node, u16 cmd, const void *request_area | |||
| 310 | case TIPC_CMD_SET_NODE_ADDR: | 285 | case TIPC_CMD_SET_NODE_ADDR: |
| 311 | rep_tlv_buf = cfg_set_own_addr(); | 286 | rep_tlv_buf = cfg_set_own_addr(); |
| 312 | break; | 287 | break; |
| 313 | case TIPC_CMD_SET_REMOTE_MNG: | ||
| 314 | rep_tlv_buf = cfg_set_remote_mng(); | ||
| 315 | break; | ||
| 316 | case TIPC_CMD_SET_MAX_PORTS: | 288 | case TIPC_CMD_SET_MAX_PORTS: |
| 317 | rep_tlv_buf = cfg_set_max_ports(); | 289 | rep_tlv_buf = cfg_set_max_ports(); |
| 318 | break; | 290 | break; |
| 319 | case TIPC_CMD_SET_NETID: | 291 | case TIPC_CMD_SET_NETID: |
| 320 | rep_tlv_buf = cfg_set_netid(); | 292 | rep_tlv_buf = cfg_set_netid(); |
| 321 | break; | 293 | break; |
| 322 | case TIPC_CMD_GET_REMOTE_MNG: | ||
| 323 | rep_tlv_buf = tipc_cfg_reply_unsigned(tipc_remote_management); | ||
| 324 | break; | ||
| 325 | case TIPC_CMD_GET_MAX_PORTS: | 294 | case TIPC_CMD_GET_MAX_PORTS: |
| 326 | rep_tlv_buf = tipc_cfg_reply_unsigned(tipc_max_ports); | 295 | rep_tlv_buf = tipc_cfg_reply_unsigned(tipc_max_ports); |
| 327 | break; | 296 | break; |
| @@ -345,6 +314,8 @@ struct sk_buff *tipc_cfg_do_cmd(u32 orig_node, u16 cmd, const void *request_area | |||
| 345 | case TIPC_CMD_SET_MAX_PUBL: | 314 | case TIPC_CMD_SET_MAX_PUBL: |
| 346 | case TIPC_CMD_GET_MAX_PUBL: | 315 | case TIPC_CMD_GET_MAX_PUBL: |
| 347 | case TIPC_CMD_SET_LOG_SIZE: | 316 | case TIPC_CMD_SET_LOG_SIZE: |
| 317 | case TIPC_CMD_SET_REMOTE_MNG: | ||
| 318 | case TIPC_CMD_GET_REMOTE_MNG: | ||
| 348 | case TIPC_CMD_DUMP_LOG: | 319 | case TIPC_CMD_DUMP_LOG: |
| 349 | rep_tlv_buf = tipc_cfg_reply_error_string(TIPC_CFG_NOT_SUPPORTED | 320 | rep_tlv_buf = tipc_cfg_reply_error_string(TIPC_CFG_NOT_SUPPORTED |
| 350 | " (obsolete command)"); | 321 | " (obsolete command)"); |
| @@ -369,75 +340,3 @@ exit: | |||
| 369 | mutex_unlock(&config_mutex); | 340 | mutex_unlock(&config_mutex); |
| 370 | return rep_tlv_buf; | 341 | return rep_tlv_buf; |
| 371 | } | 342 | } |
| 372 | |||
| 373 | static void cfg_conn_msg_event(int conid, struct sockaddr_tipc *addr, | ||
| 374 | void *usr_data, void *buf, size_t len) | ||
| 375 | { | ||
| 376 | struct tipc_cfg_msg_hdr *req_hdr; | ||
| 377 | struct tipc_cfg_msg_hdr *rep_hdr; | ||
| 378 | struct sk_buff *rep_buf; | ||
| 379 | |||
| 380 | /* Validate configuration message header (ignore invalid message) */ | ||
| 381 | req_hdr = (struct tipc_cfg_msg_hdr *)buf; | ||
| 382 | if ((len < sizeof(*req_hdr)) || | ||
| 383 | (len != TCM_ALIGN(ntohl(req_hdr->tcm_len))) || | ||
| 384 | (ntohs(req_hdr->tcm_flags) != TCM_F_REQUEST)) { | ||
| 385 | pr_warn("Invalid configuration message discarded\n"); | ||
| 386 | return; | ||
| 387 | } | ||
| 388 | |||
| 389 | /* Generate reply for request (if can't, return request) */ | ||
| 390 | rep_buf = tipc_cfg_do_cmd(addr->addr.id.node, ntohs(req_hdr->tcm_type), | ||
| 391 | buf + sizeof(*req_hdr), | ||
| 392 | len - sizeof(*req_hdr), | ||
| 393 | BUF_HEADROOM + MAX_H_SIZE + sizeof(*rep_hdr)); | ||
| 394 | if (rep_buf) { | ||
| 395 | skb_push(rep_buf, sizeof(*rep_hdr)); | ||
| 396 | rep_hdr = (struct tipc_cfg_msg_hdr *)rep_buf->data; | ||
| 397 | memcpy(rep_hdr, req_hdr, sizeof(*rep_hdr)); | ||
| 398 | rep_hdr->tcm_len = htonl(rep_buf->len); | ||
| 399 | rep_hdr->tcm_flags &= htons(~TCM_F_REQUEST); | ||
| 400 | tipc_conn_sendmsg(&cfgsrv, conid, addr, rep_buf->data, | ||
| 401 | rep_buf->len); | ||
| 402 | kfree_skb(rep_buf); | ||
| 403 | } | ||
| 404 | } | ||
| 405 | |||
| 406 | static struct sockaddr_tipc cfgsrv_addr __read_mostly = { | ||
| 407 | .family = AF_TIPC, | ||
| 408 | .addrtype = TIPC_ADDR_NAMESEQ, | ||
| 409 | .addr.nameseq.type = TIPC_CFG_SRV, | ||
| 410 | .addr.nameseq.lower = 0, | ||
| 411 | .addr.nameseq.upper = 0, | ||
| 412 | .scope = TIPC_ZONE_SCOPE | ||
| 413 | }; | ||
| 414 | |||
| 415 | static struct tipc_server cfgsrv __read_mostly = { | ||
| 416 | .saddr = &cfgsrv_addr, | ||
| 417 | .imp = TIPC_CRITICAL_IMPORTANCE, | ||
| 418 | .type = SOCK_RDM, | ||
| 419 | .max_rcvbuf_size = 64 * 1024, | ||
| 420 | .name = "cfg_server", | ||
| 421 | .tipc_conn_recvmsg = cfg_conn_msg_event, | ||
| 422 | .tipc_conn_new = NULL, | ||
| 423 | .tipc_conn_shutdown = NULL | ||
| 424 | }; | ||
| 425 | |||
| 426 | int tipc_cfg_init(void) | ||
| 427 | { | ||
| 428 | return tipc_server_start(&cfgsrv); | ||
| 429 | } | ||
| 430 | |||
| 431 | void tipc_cfg_reinit(void) | ||
| 432 | { | ||
| 433 | tipc_server_stop(&cfgsrv); | ||
| 434 | |||
| 435 | cfgsrv_addr.addr.nameseq.lower = tipc_own_addr; | ||
| 436 | cfgsrv_addr.addr.nameseq.upper = tipc_own_addr; | ||
| 437 | tipc_server_start(&cfgsrv); | ||
| 438 | } | ||
| 439 | |||
| 440 | void tipc_cfg_stop(void) | ||
| 441 | { | ||
| 442 | tipc_server_stop(&cfgsrv); | ||
| 443 | } | ||
