1 // SPDX-License-Identifier: GPL-2.0-or-later 2 /* 3 * linux/drivers/net/netconsole.c 4 * 5 * Copyright (C) 2001 Ingo Molnar <mingo@redhat.com> 6 * 7 * This file contains the implementation of an IRQ-safe, crash-safe 8 * kernel console implementation that outputs kernel messages to the 9 * network. 10 * 11 * Modification history: 12 * 13 * 2001-09-17 started by Ingo Molnar. 14 * 2003-08-11 2.6 port by Matt Mackall 15 * simplified options 16 * generic card hooks 17 * works non-modular 18 * 2003-09-07 rewritten with netpoll api 19 */ 20 21 /**************************************************************** 22 * 23 ****************************************************************/ 24 25 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt 26 27 #include <linux/mm.h> 28 #include <linux/init.h> 29 #include <linux/module.h> 30 #include <linux/slab.h> 31 #include <linux/console.h> 32 #include <linux/moduleparam.h> 33 #include <linux/kernel.h> 34 #include <linux/string.h> 35 #include <linux/netpoll.h> 36 #include <linux/inet.h> 37 #include <linux/configfs.h> 38 #include <linux/etherdevice.h> 39 #include <linux/utsname.h> 40 41 MODULE_AUTHOR("Maintainer: Matt Mackall <mpm@selenic.com>"); 42 MODULE_DESCRIPTION("Console driver for network interfaces"); 43 MODULE_LICENSE("GPL"); 44 45 #define MAX_PARAM_LENGTH 256 46 #define MAX_USERDATA_ENTRY_LENGTH 256 47 #define MAX_USERDATA_VALUE_LENGTH 200 48 /* The number 3 comes from userdata entry format characters (' ', '=', '\n') */ 49 #define MAX_USERDATA_NAME_LENGTH (MAX_USERDATA_ENTRY_LENGTH - \ 50 MAX_USERDATA_VALUE_LENGTH - 3) 51 #define MAX_USERDATA_ITEMS 16 52 #define MAX_PRINT_CHUNK 1000 53 54 static char config[MAX_PARAM_LENGTH]; 55 module_param_string(netconsole, config, MAX_PARAM_LENGTH, 0); 56 MODULE_PARM_DESC(netconsole, " netconsole=[src-port]@[src-ip]/[dev],[tgt-port]@<tgt-ip>/[tgt-macaddr]"); 57 58 static bool oops_only; 59 module_param(oops_only, bool, 0600); 60 MODULE_PARM_DESC(oops_only, "Only log oops messages"); 61 62 #define NETCONSOLE_PARAM_TARGET_PREFIX "cmdline" 63 64 #ifndef MODULE 65 static int __init option_setup(char *opt) 66 { 67 strscpy(config, opt, MAX_PARAM_LENGTH); 68 return 1; 69 } 70 __setup("netconsole=", option_setup); 71 #endif /* MODULE */ 72 73 /* Linked list of all configured targets */ 74 static LIST_HEAD(target_list); 75 76 /* This needs to be a spinlock because write_msg() cannot sleep */ 77 static DEFINE_SPINLOCK(target_list_lock); 78 79 /* 80 * Console driver for extended netconsoles. Registered on the first use to 81 * avoid unnecessarily enabling ext message formatting. 82 */ 83 static struct console netconsole_ext; 84 85 /** 86 * struct netconsole_target - Represents a configured netconsole target. 87 * @list: Links this target into the target_list. 88 * @group: Links us into the configfs subsystem hierarchy. 89 * @userdata_group: Links to the userdata configfs hierarchy 90 * @userdata_complete: Cached, formatted string of append 91 * @userdata_length: String length of userdata_complete 92 * @enabled: On / off knob to enable / disable target. 93 * Visible from userspace (read-write). 94 * We maintain a strict 1:1 correspondence between this and 95 * whether the corresponding netpoll is active or inactive. 96 * Also, other parameters of a target may be modified at 97 * runtime only when it is disabled (enabled == 0). 98 * @extended: Denotes whether console is extended or not. 99 * @release: Denotes whether kernel release version should be prepended 100 * to the message. Depends on extended console. 101 * @np: The netpoll structure for this target. 102 * Contains the other userspace visible parameters: 103 * dev_name (read-write) 104 * local_port (read-write) 105 * remote_port (read-write) 106 * local_ip (read-write) 107 * remote_ip (read-write) 108 * local_mac (read-only) 109 * remote_mac (read-write) 110 */ 111 struct netconsole_target { 112 struct list_head list; 113 #ifdef CONFIG_NETCONSOLE_DYNAMIC 114 struct config_group group; 115 struct config_group userdata_group; 116 char userdata_complete[MAX_USERDATA_ENTRY_LENGTH * MAX_USERDATA_ITEMS]; 117 size_t userdata_length; 118 #endif 119 bool enabled; 120 bool extended; 121 bool release; 122 struct netpoll np; 123 }; 124 125 #ifdef CONFIG_NETCONSOLE_DYNAMIC 126 127 static struct configfs_subsystem netconsole_subsys; 128 static DEFINE_MUTEX(dynamic_netconsole_mutex); 129 130 static int __init dynamic_netconsole_init(void) 131 { 132 config_group_init(&netconsole_subsys.su_group); 133 mutex_init(&netconsole_subsys.su_mutex); 134 return configfs_register_subsystem(&netconsole_subsys); 135 } 136 137 static void __exit dynamic_netconsole_exit(void) 138 { 139 configfs_unregister_subsystem(&netconsole_subsys); 140 } 141 142 /* 143 * Targets that were created by parsing the boot/module option string 144 * do not exist in the configfs hierarchy (and have NULL names) and will 145 * never go away, so make these a no-op for them. 146 */ 147 static void netconsole_target_get(struct netconsole_target *nt) 148 { 149 if (config_item_name(&nt->group.cg_item)) 150 config_group_get(&nt->group); 151 } 152 153 static void netconsole_target_put(struct netconsole_target *nt) 154 { 155 if (config_item_name(&nt->group.cg_item)) 156 config_group_put(&nt->group); 157 } 158 159 #else /* !CONFIG_NETCONSOLE_DYNAMIC */ 160 161 static int __init dynamic_netconsole_init(void) 162 { 163 return 0; 164 } 165 166 static void __exit dynamic_netconsole_exit(void) 167 { 168 } 169 170 /* 171 * No danger of targets going away from under us when dynamic 172 * reconfigurability is off. 173 */ 174 static void netconsole_target_get(struct netconsole_target *nt) 175 { 176 } 177 178 static void netconsole_target_put(struct netconsole_target *nt) 179 { 180 } 181 182 static void populate_configfs_item(struct netconsole_target *nt, 183 int cmdline_count) 184 { 185 } 186 #endif /* CONFIG_NETCONSOLE_DYNAMIC */ 187 188 /* Allocate and initialize with defaults. 189 * Note that these targets get their config_item fields zeroed-out. 190 */ 191 static struct netconsole_target *alloc_and_init(void) 192 { 193 struct netconsole_target *nt; 194 195 nt = kzalloc(sizeof(*nt), GFP_KERNEL); 196 if (!nt) 197 return nt; 198 199 if (IS_ENABLED(CONFIG_NETCONSOLE_EXTENDED_LOG)) 200 nt->extended = true; 201 if (IS_ENABLED(CONFIG_NETCONSOLE_PREPEND_RELEASE)) 202 nt->release = true; 203 204 nt->np.name = "netconsole"; 205 strscpy(nt->np.dev_name, "eth0", IFNAMSIZ); 206 nt->np.local_port = 6665; 207 nt->np.remote_port = 6666; 208 eth_broadcast_addr(nt->np.remote_mac); 209 210 return nt; 211 } 212 213 #ifdef CONFIG_NETCONSOLE_DYNAMIC 214 215 /* 216 * Our subsystem hierarchy is: 217 * 218 * /sys/kernel/config/netconsole/ 219 * | 220 * <target>/ 221 * | enabled 222 * | release 223 * | dev_name 224 * | local_port 225 * | remote_port 226 * | local_ip 227 * | remote_ip 228 * | local_mac 229 * | remote_mac 230 * | userdata/ 231 * | <key>/ 232 * | value 233 * | ... 234 * | 235 * <target>/... 236 */ 237 238 static struct netconsole_target *to_target(struct config_item *item) 239 { 240 struct config_group *cfg_group; 241 242 cfg_group = to_config_group(item); 243 if (!cfg_group) 244 return NULL; 245 return container_of(to_config_group(item), 246 struct netconsole_target, group); 247 } 248 249 /* Get rid of possible trailing newline, returning the new length */ 250 static void trim_newline(char *s, size_t maxlen) 251 { 252 size_t len; 253 254 len = strnlen(s, maxlen); 255 if (s[len - 1] == '\n') 256 s[len - 1] = '\0'; 257 } 258 259 /* 260 * Attribute operations for netconsole_target. 261 */ 262 263 static ssize_t enabled_show(struct config_item *item, char *buf) 264 { 265 return sysfs_emit(buf, "%d\n", to_target(item)->enabled); 266 } 267 268 static ssize_t extended_show(struct config_item *item, char *buf) 269 { 270 return sysfs_emit(buf, "%d\n", to_target(item)->extended); 271 } 272 273 static ssize_t release_show(struct config_item *item, char *buf) 274 { 275 return sysfs_emit(buf, "%d\n", to_target(item)->release); 276 } 277 278 static ssize_t dev_name_show(struct config_item *item, char *buf) 279 { 280 return sysfs_emit(buf, "%s\n", to_target(item)->np.dev_name); 281 } 282 283 static ssize_t local_port_show(struct config_item *item, char *buf) 284 { 285 return sysfs_emit(buf, "%d\n", to_target(item)->np.local_port); 286 } 287 288 static ssize_t remote_port_show(struct config_item *item, char *buf) 289 { 290 return sysfs_emit(buf, "%d\n", to_target(item)->np.remote_port); 291 } 292 293 static ssize_t local_ip_show(struct config_item *item, char *buf) 294 { 295 struct netconsole_target *nt = to_target(item); 296 297 if (nt->np.ipv6) 298 return sysfs_emit(buf, "%pI6c\n", &nt->np.local_ip.in6); 299 else 300 return sysfs_emit(buf, "%pI4\n", &nt->np.local_ip); 301 } 302 303 static ssize_t remote_ip_show(struct config_item *item, char *buf) 304 { 305 struct netconsole_target *nt = to_target(item); 306 307 if (nt->np.ipv6) 308 return sysfs_emit(buf, "%pI6c\n", &nt->np.remote_ip.in6); 309 else 310 return sysfs_emit(buf, "%pI4\n", &nt->np.remote_ip); 311 } 312 313 static ssize_t local_mac_show(struct config_item *item, char *buf) 314 { 315 struct net_device *dev = to_target(item)->np.dev; 316 static const u8 bcast[ETH_ALEN] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; 317 318 return sysfs_emit(buf, "%pM\n", dev ? dev->dev_addr : bcast); 319 } 320 321 static ssize_t remote_mac_show(struct config_item *item, char *buf) 322 { 323 return sysfs_emit(buf, "%pM\n", to_target(item)->np.remote_mac); 324 } 325 326 /* 327 * This one is special -- targets created through the configfs interface 328 * are not enabled (and the corresponding netpoll activated) by default. 329 * The user is expected to set the desired parameters first (which 330 * would enable him to dynamically add new netpoll targets for new 331 * network interfaces as and when they come up). 332 */ 333 static ssize_t enabled_store(struct config_item *item, 334 const char *buf, size_t count) 335 { 336 struct netconsole_target *nt = to_target(item); 337 unsigned long flags; 338 bool enabled; 339 int err; 340 341 mutex_lock(&dynamic_netconsole_mutex); 342 err = kstrtobool(buf, &enabled); 343 if (err) 344 goto out_unlock; 345 346 err = -EINVAL; 347 if (enabled == nt->enabled) { 348 pr_info("network logging has already %s\n", 349 nt->enabled ? "started" : "stopped"); 350 goto out_unlock; 351 } 352 353 if (enabled) { /* true */ 354 if (nt->release && !nt->extended) { 355 pr_err("Not enabling netconsole. Release feature requires extended log message"); 356 goto out_unlock; 357 } 358 359 if (nt->extended && !console_is_registered(&netconsole_ext)) 360 register_console(&netconsole_ext); 361 362 /* 363 * Skip netpoll_parse_options() -- all the attributes are 364 * already configured via configfs. Just print them out. 365 */ 366 netpoll_print_options(&nt->np); 367 368 err = netpoll_setup(&nt->np); 369 if (err) 370 goto out_unlock; 371 372 nt->enabled = true; 373 pr_info("network logging started\n"); 374 } else { /* false */ 375 /* We need to disable the netconsole before cleaning it up 376 * otherwise we might end up in write_msg() with 377 * nt->np.dev == NULL and nt->enabled == true 378 */ 379 spin_lock_irqsave(&target_list_lock, flags); 380 nt->enabled = false; 381 spin_unlock_irqrestore(&target_list_lock, flags); 382 netpoll_cleanup(&nt->np); 383 } 384 385 mutex_unlock(&dynamic_netconsole_mutex); 386 return strnlen(buf, count); 387 out_unlock: 388 mutex_unlock(&dynamic_netconsole_mutex); 389 return err; 390 } 391 392 static ssize_t release_store(struct config_item *item, const char *buf, 393 size_t count) 394 { 395 struct netconsole_target *nt = to_target(item); 396 bool release; 397 int err; 398 399 mutex_lock(&dynamic_netconsole_mutex); 400 if (nt->enabled) { 401 pr_err("target (%s) is enabled, disable to update parameters\n", 402 config_item_name(&nt->group.cg_item)); 403 err = -EINVAL; 404 goto out_unlock; 405 } 406 407 err = kstrtobool(buf, &release); 408 if (err) 409 goto out_unlock; 410 411 nt->release = release; 412 413 mutex_unlock(&dynamic_netconsole_mutex); 414 return strnlen(buf, count); 415 out_unlock: 416 mutex_unlock(&dynamic_netconsole_mutex); 417 return err; 418 } 419 420 static ssize_t extended_store(struct config_item *item, const char *buf, 421 size_t count) 422 { 423 struct netconsole_target *nt = to_target(item); 424 bool extended; 425 int err; 426 427 mutex_lock(&dynamic_netconsole_mutex); 428 if (nt->enabled) { 429 pr_err("target (%s) is enabled, disable to update parameters\n", 430 config_item_name(&nt->group.cg_item)); 431 err = -EINVAL; 432 goto out_unlock; 433 } 434 435 err = kstrtobool(buf, &extended); 436 if (err) 437 goto out_unlock; 438 439 nt->extended = extended; 440 441 mutex_unlock(&dynamic_netconsole_mutex); 442 return strnlen(buf, count); 443 out_unlock: 444 mutex_unlock(&dynamic_netconsole_mutex); 445 return err; 446 } 447 448 static ssize_t dev_name_store(struct config_item *item, const char *buf, 449 size_t count) 450 { 451 struct netconsole_target *nt = to_target(item); 452 453 mutex_lock(&dynamic_netconsole_mutex); 454 if (nt->enabled) { 455 pr_err("target (%s) is enabled, disable to update parameters\n", 456 config_item_name(&nt->group.cg_item)); 457 mutex_unlock(&dynamic_netconsole_mutex); 458 return -EINVAL; 459 } 460 461 strscpy(nt->np.dev_name, buf, IFNAMSIZ); 462 trim_newline(nt->np.dev_name, IFNAMSIZ); 463 464 mutex_unlock(&dynamic_netconsole_mutex); 465 return strnlen(buf, count); 466 } 467 468 static ssize_t local_port_store(struct config_item *item, const char *buf, 469 size_t count) 470 { 471 struct netconsole_target *nt = to_target(item); 472 int rv = -EINVAL; 473 474 mutex_lock(&dynamic_netconsole_mutex); 475 if (nt->enabled) { 476 pr_err("target (%s) is enabled, disable to update parameters\n", 477 config_item_name(&nt->group.cg_item)); 478 goto out_unlock; 479 } 480 481 rv = kstrtou16(buf, 10, &nt->np.local_port); 482 if (rv < 0) 483 goto out_unlock; 484 mutex_unlock(&dynamic_netconsole_mutex); 485 return strnlen(buf, count); 486 out_unlock: 487 mutex_unlock(&dynamic_netconsole_mutex); 488 return rv; 489 } 490 491 static ssize_t remote_port_store(struct config_item *item, 492 const char *buf, size_t count) 493 { 494 struct netconsole_target *nt = to_target(item); 495 int rv = -EINVAL; 496 497 mutex_lock(&dynamic_netconsole_mutex); 498 if (nt->enabled) { 499 pr_err("target (%s) is enabled, disable to update parameters\n", 500 config_item_name(&nt->group.cg_item)); 501 goto out_unlock; 502 } 503 504 rv = kstrtou16(buf, 10, &nt->np.remote_port); 505 if (rv < 0) 506 goto out_unlock; 507 mutex_unlock(&dynamic_netconsole_mutex); 508 return strnlen(buf, count); 509 out_unlock: 510 mutex_unlock(&dynamic_netconsole_mutex); 511 return rv; 512 } 513 514 static ssize_t local_ip_store(struct config_item *item, const char *buf, 515 size_t count) 516 { 517 struct netconsole_target *nt = to_target(item); 518 519 mutex_lock(&dynamic_netconsole_mutex); 520 if (nt->enabled) { 521 pr_err("target (%s) is enabled, disable to update parameters\n", 522 config_item_name(&nt->group.cg_item)); 523 goto out_unlock; 524 } 525 526 if (strnchr(buf, count, ':')) { 527 const char *end; 528 529 if (in6_pton(buf, count, nt->np.local_ip.in6.s6_addr, -1, &end) > 0) { 530 if (*end && *end != '\n') { 531 pr_err("invalid IPv6 address at: <%c>\n", *end); 532 goto out_unlock; 533 } 534 nt->np.ipv6 = true; 535 } else 536 goto out_unlock; 537 } else { 538 if (!nt->np.ipv6) 539 nt->np.local_ip.ip = in_aton(buf); 540 else 541 goto out_unlock; 542 } 543 544 mutex_unlock(&dynamic_netconsole_mutex); 545 return strnlen(buf, count); 546 out_unlock: 547 mutex_unlock(&dynamic_netconsole_mutex); 548 return -EINVAL; 549 } 550 551 static ssize_t remote_ip_store(struct config_item *item, const char *buf, 552 size_t count) 553 { 554 struct netconsole_target *nt = to_target(item); 555 556 mutex_lock(&dynamic_netconsole_mutex); 557 if (nt->enabled) { 558 pr_err("target (%s) is enabled, disable to update parameters\n", 559 config_item_name(&nt->group.cg_item)); 560 goto out_unlock; 561 } 562 563 if (strnchr(buf, count, ':')) { 564 const char *end; 565 566 if (in6_pton(buf, count, nt->np.remote_ip.in6.s6_addr, -1, &end) > 0) { 567 if (*end && *end != '\n') { 568 pr_err("invalid IPv6 address at: <%c>\n", *end); 569 goto out_unlock; 570 } 571 nt->np.ipv6 = true; 572 } else 573 goto out_unlock; 574 } else { 575 if (!nt->np.ipv6) 576 nt->np.remote_ip.ip = in_aton(buf); 577 else 578 goto out_unlock; 579 } 580 581 mutex_unlock(&dynamic_netconsole_mutex); 582 return strnlen(buf, count); 583 out_unlock: 584 mutex_unlock(&dynamic_netconsole_mutex); 585 return -EINVAL; 586 } 587 588 static ssize_t remote_mac_store(struct config_item *item, const char *buf, 589 size_t count) 590 { 591 struct netconsole_target *nt = to_target(item); 592 u8 remote_mac[ETH_ALEN]; 593 594 mutex_lock(&dynamic_netconsole_mutex); 595 if (nt->enabled) { 596 pr_err("target (%s) is enabled, disable to update parameters\n", 597 config_item_name(&nt->group.cg_item)); 598 goto out_unlock; 599 } 600 601 if (!mac_pton(buf, remote_mac)) 602 goto out_unlock; 603 if (buf[3 * ETH_ALEN - 1] && buf[3 * ETH_ALEN - 1] != '\n') 604 goto out_unlock; 605 memcpy(nt->np.remote_mac, remote_mac, ETH_ALEN); 606 607 mutex_unlock(&dynamic_netconsole_mutex); 608 return strnlen(buf, count); 609 out_unlock: 610 mutex_unlock(&dynamic_netconsole_mutex); 611 return -EINVAL; 612 } 613 614 struct userdatum { 615 struct config_item item; 616 char value[MAX_USERDATA_VALUE_LENGTH]; 617 }; 618 619 static struct userdatum *to_userdatum(struct config_item *item) 620 { 621 return container_of(item, struct userdatum, item); 622 } 623 624 struct userdata { 625 struct config_group group; 626 }; 627 628 static struct userdata *to_userdata(struct config_item *item) 629 { 630 return container_of(to_config_group(item), struct userdata, group); 631 } 632 633 static struct netconsole_target *userdata_to_target(struct userdata *ud) 634 { 635 struct config_group *netconsole_group; 636 637 netconsole_group = to_config_group(ud->group.cg_item.ci_parent); 638 return to_target(&netconsole_group->cg_item); 639 } 640 641 static ssize_t userdatum_value_show(struct config_item *item, char *buf) 642 { 643 return sysfs_emit(buf, "%s\n", &(to_userdatum(item)->value[0])); 644 } 645 646 static void update_userdata(struct netconsole_target *nt) 647 { 648 int complete_idx = 0, child_count = 0; 649 struct list_head *entry; 650 651 /* Clear the current string in case the last userdatum was deleted */ 652 nt->userdata_length = 0; 653 nt->userdata_complete[0] = 0; 654 655 list_for_each(entry, &nt->userdata_group.cg_children) { 656 struct userdatum *udm_item; 657 struct config_item *item; 658 659 if (child_count >= MAX_USERDATA_ITEMS) 660 break; 661 child_count++; 662 663 item = container_of(entry, struct config_item, ci_entry); 664 udm_item = to_userdatum(item); 665 666 /* Skip userdata with no value set */ 667 if (strnlen(udm_item->value, MAX_USERDATA_VALUE_LENGTH) == 0) 668 continue; 669 670 /* This doesn't overflow userdata_complete since it will write 671 * one entry length (1/MAX_USERDATA_ITEMS long), entry count is 672 * checked to not exceed MAX items with child_count above 673 */ 674 complete_idx += scnprintf(&nt->userdata_complete[complete_idx], 675 MAX_USERDATA_ENTRY_LENGTH, " %s=%s\n", 676 item->ci_name, udm_item->value); 677 } 678 nt->userdata_length = strnlen(nt->userdata_complete, 679 sizeof(nt->userdata_complete)); 680 } 681 682 static ssize_t userdatum_value_store(struct config_item *item, const char *buf, 683 size_t count) 684 { 685 struct userdatum *udm = to_userdatum(item); 686 struct netconsole_target *nt; 687 struct userdata *ud; 688 int ret; 689 690 if (count > MAX_USERDATA_VALUE_LENGTH) 691 return -EMSGSIZE; 692 693 mutex_lock(&dynamic_netconsole_mutex); 694 695 ret = strscpy(udm->value, buf, sizeof(udm->value)); 696 if (ret < 0) 697 goto out_unlock; 698 trim_newline(udm->value, sizeof(udm->value)); 699 700 ud = to_userdata(item->ci_parent); 701 nt = userdata_to_target(ud); 702 update_userdata(nt); 703 704 mutex_unlock(&dynamic_netconsole_mutex); 705 return count; 706 out_unlock: 707 mutex_unlock(&dynamic_netconsole_mutex); 708 return ret; 709 } 710 711 CONFIGFS_ATTR(userdatum_, value); 712 713 static struct configfs_attribute *userdatum_attrs[] = { 714 &userdatum_attr_value, 715 NULL, 716 }; 717 718 static void userdatum_release(struct config_item *item) 719 { 720 kfree(to_userdatum(item)); 721 } 722 723 static struct configfs_item_operations userdatum_ops = { 724 .release = userdatum_release, 725 }; 726 727 static const struct config_item_type userdatum_type = { 728 .ct_item_ops = &userdatum_ops, 729 .ct_attrs = userdatum_attrs, 730 .ct_owner = THIS_MODULE, 731 }; 732 733 static struct config_item *userdatum_make_item(struct config_group *group, 734 const char *name) 735 { 736 struct netconsole_target *nt; 737 struct userdatum *udm; 738 struct userdata *ud; 739 size_t child_count; 740 741 if (strlen(name) > MAX_USERDATA_NAME_LENGTH) 742 return ERR_PTR(-ENAMETOOLONG); 743 744 ud = to_userdata(&group->cg_item); 745 nt = userdata_to_target(ud); 746 child_count = list_count_nodes(&nt->userdata_group.cg_children); 747 if (child_count >= MAX_USERDATA_ITEMS) 748 return ERR_PTR(-ENOSPC); 749 750 udm = kzalloc(sizeof(*udm), GFP_KERNEL); 751 if (!udm) 752 return ERR_PTR(-ENOMEM); 753 754 config_item_init_type_name(&udm->item, name, &userdatum_type); 755 return &udm->item; 756 } 757 758 static void userdatum_drop(struct config_group *group, struct config_item *item) 759 { 760 struct netconsole_target *nt; 761 struct userdata *ud; 762 763 ud = to_userdata(&group->cg_item); 764 nt = userdata_to_target(ud); 765 766 mutex_lock(&dynamic_netconsole_mutex); 767 update_userdata(nt); 768 config_item_put(item); 769 mutex_unlock(&dynamic_netconsole_mutex); 770 } 771 772 static struct configfs_attribute *userdata_attrs[] = { 773 NULL, 774 }; 775 776 static struct configfs_group_operations userdata_ops = { 777 .make_item = userdatum_make_item, 778 .drop_item = userdatum_drop, 779 }; 780 781 static struct config_item_type userdata_type = { 782 .ct_item_ops = &userdatum_ops, 783 .ct_group_ops = &userdata_ops, 784 .ct_attrs = userdata_attrs, 785 .ct_owner = THIS_MODULE, 786 }; 787 788 CONFIGFS_ATTR(, enabled); 789 CONFIGFS_ATTR(, extended); 790 CONFIGFS_ATTR(, dev_name); 791 CONFIGFS_ATTR(, local_port); 792 CONFIGFS_ATTR(, remote_port); 793 CONFIGFS_ATTR(, local_ip); 794 CONFIGFS_ATTR(, remote_ip); 795 CONFIGFS_ATTR_RO(, local_mac); 796 CONFIGFS_ATTR(, remote_mac); 797 CONFIGFS_ATTR(, release); 798 799 static struct configfs_attribute *netconsole_target_attrs[] = { 800 &attr_enabled, 801 &attr_extended, 802 &attr_release, 803 &attr_dev_name, 804 &attr_local_port, 805 &attr_remote_port, 806 &attr_local_ip, 807 &attr_remote_ip, 808 &attr_local_mac, 809 &attr_remote_mac, 810 NULL, 811 }; 812 813 /* 814 * Item operations and type for netconsole_target. 815 */ 816 817 static void netconsole_target_release(struct config_item *item) 818 { 819 kfree(to_target(item)); 820 } 821 822 static struct configfs_item_operations netconsole_target_item_ops = { 823 .release = netconsole_target_release, 824 }; 825 826 static const struct config_item_type netconsole_target_type = { 827 .ct_attrs = netconsole_target_attrs, 828 .ct_item_ops = &netconsole_target_item_ops, 829 .ct_owner = THIS_MODULE, 830 }; 831 832 static void init_target_config_group(struct netconsole_target *nt, 833 const char *name) 834 { 835 config_group_init_type_name(&nt->group, name, &netconsole_target_type); 836 config_group_init_type_name(&nt->userdata_group, "userdata", 837 &userdata_type); 838 configfs_add_default_group(&nt->userdata_group, &nt->group); 839 } 840 841 static struct netconsole_target *find_cmdline_target(const char *name) 842 { 843 struct netconsole_target *nt, *ret = NULL; 844 unsigned long flags; 845 846 spin_lock_irqsave(&target_list_lock, flags); 847 list_for_each_entry(nt, &target_list, list) { 848 if (!strcmp(nt->group.cg_item.ci_name, name)) { 849 ret = nt; 850 break; 851 } 852 } 853 spin_unlock_irqrestore(&target_list_lock, flags); 854 855 return ret; 856 } 857 858 /* 859 * Group operations and type for netconsole_subsys. 860 */ 861 862 static struct config_group *make_netconsole_target(struct config_group *group, 863 const char *name) 864 { 865 struct netconsole_target *nt; 866 unsigned long flags; 867 868 /* Checking if a target by this name was created at boot time. If so, 869 * attach a configfs entry to that target. This enables dynamic 870 * control. 871 */ 872 if (!strncmp(name, NETCONSOLE_PARAM_TARGET_PREFIX, 873 strlen(NETCONSOLE_PARAM_TARGET_PREFIX))) { 874 nt = find_cmdline_target(name); 875 if (nt) { 876 init_target_config_group(nt, name); 877 return &nt->group; 878 } 879 } 880 881 nt = alloc_and_init(); 882 if (!nt) 883 return ERR_PTR(-ENOMEM); 884 885 /* Initialize the config_group member */ 886 init_target_config_group(nt, name); 887 888 /* Adding, but it is disabled */ 889 spin_lock_irqsave(&target_list_lock, flags); 890 list_add(&nt->list, &target_list); 891 spin_unlock_irqrestore(&target_list_lock, flags); 892 893 return &nt->group; 894 } 895 896 static void drop_netconsole_target(struct config_group *group, 897 struct config_item *item) 898 { 899 unsigned long flags; 900 struct netconsole_target *nt = to_target(item); 901 902 spin_lock_irqsave(&target_list_lock, flags); 903 list_del(&nt->list); 904 spin_unlock_irqrestore(&target_list_lock, flags); 905 906 /* 907 * The target may have never been enabled, or was manually disabled 908 * before being removed so netpoll may have already been cleaned up. 909 */ 910 if (nt->enabled) 911 netpoll_cleanup(&nt->np); 912 913 config_item_put(&nt->group.cg_item); 914 } 915 916 static struct configfs_group_operations netconsole_subsys_group_ops = { 917 .make_group = make_netconsole_target, 918 .drop_item = drop_netconsole_target, 919 }; 920 921 static const struct config_item_type netconsole_subsys_type = { 922 .ct_group_ops = &netconsole_subsys_group_ops, 923 .ct_owner = THIS_MODULE, 924 }; 925 926 /* The netconsole configfs subsystem */ 927 static struct configfs_subsystem netconsole_subsys = { 928 .su_group = { 929 .cg_item = { 930 .ci_namebuf = "netconsole", 931 .ci_type = &netconsole_subsys_type, 932 }, 933 }, 934 }; 935 936 static void populate_configfs_item(struct netconsole_target *nt, 937 int cmdline_count) 938 { 939 char target_name[16]; 940 941 snprintf(target_name, sizeof(target_name), "%s%d", 942 NETCONSOLE_PARAM_TARGET_PREFIX, cmdline_count); 943 init_target_config_group(nt, target_name); 944 } 945 946 #endif /* CONFIG_NETCONSOLE_DYNAMIC */ 947 948 /* Handle network interface device notifications */ 949 static int netconsole_netdev_event(struct notifier_block *this, 950 unsigned long event, void *ptr) 951 { 952 unsigned long flags; 953 struct netconsole_target *nt; 954 struct net_device *dev = netdev_notifier_info_to_dev(ptr); 955 bool stopped = false; 956 957 if (!(event == NETDEV_CHANGENAME || event == NETDEV_UNREGISTER || 958 event == NETDEV_RELEASE || event == NETDEV_JOIN)) 959 goto done; 960 961 spin_lock_irqsave(&target_list_lock, flags); 962 restart: 963 list_for_each_entry(nt, &target_list, list) { 964 netconsole_target_get(nt); 965 if (nt->np.dev == dev) { 966 switch (event) { 967 case NETDEV_CHANGENAME: 968 strscpy(nt->np.dev_name, dev->name, IFNAMSIZ); 969 break; 970 case NETDEV_RELEASE: 971 case NETDEV_JOIN: 972 case NETDEV_UNREGISTER: 973 /* rtnl_lock already held 974 * we might sleep in __netpoll_cleanup() 975 */ 976 nt->enabled = false; 977 spin_unlock_irqrestore(&target_list_lock, flags); 978 979 __netpoll_cleanup(&nt->np); 980 981 spin_lock_irqsave(&target_list_lock, flags); 982 netdev_put(nt->np.dev, &nt->np.dev_tracker); 983 nt->np.dev = NULL; 984 stopped = true; 985 netconsole_target_put(nt); 986 goto restart; 987 } 988 } 989 netconsole_target_put(nt); 990 } 991 spin_unlock_irqrestore(&target_list_lock, flags); 992 if (stopped) { 993 const char *msg = "had an event"; 994 995 switch (event) { 996 case NETDEV_UNREGISTER: 997 msg = "unregistered"; 998 break; 999 case NETDEV_RELEASE: 1000 msg = "released slaves"; 1001 break; 1002 case NETDEV_JOIN: 1003 msg = "is joining a master device"; 1004 break; 1005 } 1006 pr_info("network logging stopped on interface %s as it %s\n", 1007 dev->name, msg); 1008 } 1009 1010 done: 1011 return NOTIFY_DONE; 1012 } 1013 1014 static struct notifier_block netconsole_netdev_notifier = { 1015 .notifier_call = netconsole_netdev_event, 1016 }; 1017 1018 /** 1019 * send_ext_msg_udp - send extended log message to target 1020 * @nt: target to send message to 1021 * @msg: extended log message to send 1022 * @msg_len: length of message 1023 * 1024 * Transfer extended log @msg to @nt. If @msg is longer than 1025 * MAX_PRINT_CHUNK, it'll be split and transmitted in multiple chunks with 1026 * ncfrag header field added to identify them. 1027 */ 1028 static void send_ext_msg_udp(struct netconsole_target *nt, const char *msg, 1029 int msg_len) 1030 { 1031 static char buf[MAX_PRINT_CHUNK]; /* protected by target_list_lock */ 1032 const char *header, *body; 1033 int offset = 0; 1034 int header_len, body_len; 1035 const char *msg_ready = msg; 1036 const char *release; 1037 int release_len = 0; 1038 int userdata_len = 0; 1039 char *userdata = NULL; 1040 1041 #ifdef CONFIG_NETCONSOLE_DYNAMIC 1042 userdata = nt->userdata_complete; 1043 userdata_len = nt->userdata_length; 1044 #endif 1045 1046 if (nt->release) { 1047 release = init_utsname()->release; 1048 release_len = strlen(release) + 1; 1049 } 1050 1051 if (msg_len + release_len + userdata_len <= MAX_PRINT_CHUNK) { 1052 /* No fragmentation needed */ 1053 if (nt->release) { 1054 scnprintf(buf, MAX_PRINT_CHUNK, "%s,%s", release, msg); 1055 msg_len += release_len; 1056 } else { 1057 memcpy(buf, msg, msg_len); 1058 } 1059 1060 if (userdata) 1061 msg_len += scnprintf(&buf[msg_len], 1062 MAX_PRINT_CHUNK - msg_len, 1063 "%s", userdata); 1064 1065 msg_ready = buf; 1066 netpoll_send_udp(&nt->np, msg_ready, msg_len); 1067 return; 1068 } 1069 1070 /* need to insert extra header fields, detect header and body */ 1071 header = msg; 1072 body = memchr(msg, ';', msg_len); 1073 if (WARN_ON_ONCE(!body)) 1074 return; 1075 1076 header_len = body - header; 1077 body_len = msg_len - header_len - 1; 1078 body++; 1079 1080 /* 1081 * Transfer multiple chunks with the following extra header. 1082 * "ncfrag=<byte-offset>/<total-bytes>" 1083 */ 1084 if (nt->release) 1085 scnprintf(buf, MAX_PRINT_CHUNK, "%s,", release); 1086 memcpy(buf + release_len, header, header_len); 1087 header_len += release_len; 1088 1089 while (offset < body_len + userdata_len) { 1090 int this_header = header_len; 1091 int this_offset = 0; 1092 int this_chunk = 0; 1093 1094 this_header += scnprintf(buf + this_header, 1095 sizeof(buf) - this_header, 1096 ",ncfrag=%d/%d;", offset, 1097 body_len + userdata_len); 1098 1099 /* Not all body data has been written yet */ 1100 if (offset < body_len) { 1101 this_chunk = min(body_len - offset, 1102 MAX_PRINT_CHUNK - this_header); 1103 if (WARN_ON_ONCE(this_chunk <= 0)) 1104 return; 1105 memcpy(buf + this_header, body + offset, this_chunk); 1106 this_offset += this_chunk; 1107 } 1108 /* Body is fully written and there is pending userdata to write, 1109 * append userdata in this chunk 1110 */ 1111 if (offset + this_offset >= body_len && 1112 offset + this_offset < userdata_len + body_len) { 1113 int sent_userdata = (offset + this_offset) - body_len; 1114 int preceding_bytes = this_chunk + this_header; 1115 1116 if (WARN_ON_ONCE(sent_userdata < 0)) 1117 return; 1118 1119 this_chunk = min(userdata_len - sent_userdata, 1120 MAX_PRINT_CHUNK - preceding_bytes); 1121 if (WARN_ON_ONCE(this_chunk <= 0)) 1122 return; 1123 memcpy(buf + this_header + this_offset, 1124 userdata + sent_userdata, 1125 this_chunk); 1126 this_offset += this_chunk; 1127 } 1128 1129 netpoll_send_udp(&nt->np, buf, this_header + this_offset); 1130 offset += this_offset; 1131 } 1132 } 1133 1134 static void write_ext_msg(struct console *con, const char *msg, 1135 unsigned int len) 1136 { 1137 struct netconsole_target *nt; 1138 unsigned long flags; 1139 1140 if ((oops_only && !oops_in_progress) || list_empty(&target_list)) 1141 return; 1142 1143 spin_lock_irqsave(&target_list_lock, flags); 1144 list_for_each_entry(nt, &target_list, list) 1145 if (nt->extended && nt->enabled && netif_running(nt->np.dev)) 1146 send_ext_msg_udp(nt, msg, len); 1147 spin_unlock_irqrestore(&target_list_lock, flags); 1148 } 1149 1150 static void write_msg(struct console *con, const char *msg, unsigned int len) 1151 { 1152 int frag, left; 1153 unsigned long flags; 1154 struct netconsole_target *nt; 1155 const char *tmp; 1156 1157 if (oops_only && !oops_in_progress) 1158 return; 1159 /* Avoid taking lock and disabling interrupts unnecessarily */ 1160 if (list_empty(&target_list)) 1161 return; 1162 1163 spin_lock_irqsave(&target_list_lock, flags); 1164 list_for_each_entry(nt, &target_list, list) { 1165 if (!nt->extended && nt->enabled && netif_running(nt->np.dev)) { 1166 /* 1167 * We nest this inside the for-each-target loop above 1168 * so that we're able to get as much logging out to 1169 * at least one target if we die inside here, instead 1170 * of unnecessarily keeping all targets in lock-step. 1171 */ 1172 tmp = msg; 1173 for (left = len; left;) { 1174 frag = min(left, MAX_PRINT_CHUNK); 1175 netpoll_send_udp(&nt->np, tmp, frag); 1176 tmp += frag; 1177 left -= frag; 1178 } 1179 } 1180 } 1181 spin_unlock_irqrestore(&target_list_lock, flags); 1182 } 1183 1184 /* Allocate new target (from boot/module param) and setup netpoll for it */ 1185 static struct netconsole_target *alloc_param_target(char *target_config, 1186 int cmdline_count) 1187 { 1188 struct netconsole_target *nt; 1189 int err; 1190 1191 nt = alloc_and_init(); 1192 if (!nt) { 1193 err = -ENOMEM; 1194 goto fail; 1195 } 1196 1197 if (*target_config == '+') { 1198 nt->extended = true; 1199 target_config++; 1200 } 1201 1202 if (*target_config == 'r') { 1203 if (!nt->extended) { 1204 pr_err("Netconsole configuration error. Release feature requires extended log message"); 1205 err = -EINVAL; 1206 goto fail; 1207 } 1208 nt->release = true; 1209 target_config++; 1210 } 1211 1212 /* Parse parameters and setup netpoll */ 1213 err = netpoll_parse_options(&nt->np, target_config); 1214 if (err) 1215 goto fail; 1216 1217 err = netpoll_setup(&nt->np); 1218 if (err) 1219 goto fail; 1220 1221 populate_configfs_item(nt, cmdline_count); 1222 nt->enabled = true; 1223 1224 return nt; 1225 1226 fail: 1227 kfree(nt); 1228 return ERR_PTR(err); 1229 } 1230 1231 /* Cleanup netpoll for given target (from boot/module param) and free it */ 1232 static void free_param_target(struct netconsole_target *nt) 1233 { 1234 netpoll_cleanup(&nt->np); 1235 kfree(nt); 1236 } 1237 1238 static struct console netconsole_ext = { 1239 .name = "netcon_ext", 1240 .flags = CON_ENABLED | CON_EXTENDED, 1241 .write = write_ext_msg, 1242 }; 1243 1244 static struct console netconsole = { 1245 .name = "netcon", 1246 .flags = CON_ENABLED, 1247 .write = write_msg, 1248 }; 1249 1250 static int __init init_netconsole(void) 1251 { 1252 int err; 1253 struct netconsole_target *nt, *tmp; 1254 unsigned int count = 0; 1255 bool extended = false; 1256 unsigned long flags; 1257 char *target_config; 1258 char *input = config; 1259 1260 if (strnlen(input, MAX_PARAM_LENGTH)) { 1261 while ((target_config = strsep(&input, ";"))) { 1262 nt = alloc_param_target(target_config, count); 1263 if (IS_ERR(nt)) { 1264 if (IS_ENABLED(CONFIG_NETCONSOLE_DYNAMIC)) 1265 continue; 1266 err = PTR_ERR(nt); 1267 goto fail; 1268 } 1269 /* Dump existing printks when we register */ 1270 if (nt->extended) { 1271 extended = true; 1272 netconsole_ext.flags |= CON_PRINTBUFFER; 1273 } else { 1274 netconsole.flags |= CON_PRINTBUFFER; 1275 } 1276 1277 spin_lock_irqsave(&target_list_lock, flags); 1278 list_add(&nt->list, &target_list); 1279 spin_unlock_irqrestore(&target_list_lock, flags); 1280 count++; 1281 } 1282 } 1283 1284 err = register_netdevice_notifier(&netconsole_netdev_notifier); 1285 if (err) 1286 goto fail; 1287 1288 err = dynamic_netconsole_init(); 1289 if (err) 1290 goto undonotifier; 1291 1292 if (extended) 1293 register_console(&netconsole_ext); 1294 register_console(&netconsole); 1295 pr_info("network logging started\n"); 1296 1297 return err; 1298 1299 undonotifier: 1300 unregister_netdevice_notifier(&netconsole_netdev_notifier); 1301 1302 fail: 1303 pr_err("cleaning up\n"); 1304 1305 /* 1306 * Remove all targets and destroy them (only targets created 1307 * from the boot/module option exist here). Skipping the list 1308 * lock is safe here, and netpoll_cleanup() will sleep. 1309 */ 1310 list_for_each_entry_safe(nt, tmp, &target_list, list) { 1311 list_del(&nt->list); 1312 free_param_target(nt); 1313 } 1314 1315 return err; 1316 } 1317 1318 static void __exit cleanup_netconsole(void) 1319 { 1320 struct netconsole_target *nt, *tmp; 1321 1322 if (console_is_registered(&netconsole_ext)) 1323 unregister_console(&netconsole_ext); 1324 unregister_console(&netconsole); 1325 dynamic_netconsole_exit(); 1326 unregister_netdevice_notifier(&netconsole_netdev_notifier); 1327 1328 /* 1329 * Targets created via configfs pin references on our module 1330 * and would first be rmdir(2)'ed from userspace. We reach 1331 * here only when they are already destroyed, and only those 1332 * created from the boot/module option are left, so remove and 1333 * destroy them. Skipping the list lock is safe here, and 1334 * netpoll_cleanup() will sleep. 1335 */ 1336 list_for_each_entry_safe(nt, tmp, &target_list, list) { 1337 list_del(&nt->list); 1338 free_param_target(nt); 1339 } 1340 } 1341 1342 /* 1343 * Use late_initcall to ensure netconsole is 1344 * initialized after network device driver if built-in. 1345 * 1346 * late_initcall() and module_init() are identical if built as module. 1347 */ 1348 late_initcall(init_netconsole); 1349 module_exit(cleanup_netconsole); 1350