aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--net/ipv4/devinet.c69
1 files changed, 20 insertions, 49 deletions
diff --git a/net/ipv4/devinet.c b/net/ipv4/devinet.c
index a3a7d301736e..9e2747aab252 100644
--- a/net/ipv4/devinet.c
+++ b/net/ipv4/devinet.c
@@ -1430,11 +1430,8 @@ int ipv4_doint_and_flush_strategy(ctl_table *table, int __user *name, int nlen,
1430 1430
1431static struct devinet_sysctl_table { 1431static struct devinet_sysctl_table {
1432 struct ctl_table_header *sysctl_header; 1432 struct ctl_table_header *sysctl_header;
1433 ctl_table devinet_vars[__NET_IPV4_CONF_MAX]; 1433 struct ctl_table devinet_vars[__NET_IPV4_CONF_MAX];
1434 ctl_table devinet_dev[2]; 1434 char *dev_name;
1435 ctl_table devinet_conf_dir[2];
1436 ctl_table devinet_proto_dir[2];
1437 ctl_table devinet_root_dir[2];
1438} devinet_sysctl = { 1435} devinet_sysctl = {
1439 .devinet_vars = { 1436 .devinet_vars = {
1440 DEVINET_SYSCTL_COMPLEX_ENTRY(FORWARDING, "forwarding", 1437 DEVINET_SYSCTL_COMPLEX_ENTRY(FORWARDING, "forwarding",
@@ -1466,38 +1463,6 @@ static struct devinet_sysctl_table {
1466 DEVINET_SYSCTL_FLUSHING_ENTRY(PROMOTE_SECONDARIES, 1463 DEVINET_SYSCTL_FLUSHING_ENTRY(PROMOTE_SECONDARIES,
1467 "promote_secondaries"), 1464 "promote_secondaries"),
1468 }, 1465 },
1469 .devinet_dev = {
1470 {
1471 .ctl_name = NET_PROTO_CONF_ALL,
1472 .procname = "all",
1473 .mode = 0555,
1474 .child = devinet_sysctl.devinet_vars,
1475 },
1476 },
1477 .devinet_conf_dir = {
1478 {
1479 .ctl_name = NET_IPV4_CONF,
1480 .procname = "conf",
1481 .mode = 0555,
1482 .child = devinet_sysctl.devinet_dev,
1483 },
1484 },
1485 .devinet_proto_dir = {
1486 {
1487 .ctl_name = NET_IPV4,
1488 .procname = "ipv4",
1489 .mode = 0555,
1490 .child = devinet_sysctl.devinet_conf_dir,
1491 },
1492 },
1493 .devinet_root_dir = {
1494 {
1495 .ctl_name = CTL_NET,
1496 .procname = "net",
1497 .mode = 0555,
1498 .child = devinet_sysctl.devinet_proto_dir,
1499 },
1500 },
1501}; 1466};
1502 1467
1503static void __devinet_sysctl_register(char *dev_name, int ctl_name, 1468static void __devinet_sysctl_register(char *dev_name, int ctl_name,
@@ -1506,6 +1471,16 @@ static void __devinet_sysctl_register(char *dev_name, int ctl_name,
1506 int i; 1471 int i;
1507 struct devinet_sysctl_table *t; 1472 struct devinet_sysctl_table *t;
1508 1473
1474#define DEVINET_CTL_PATH_DEV 3
1475
1476 struct ctl_path devinet_ctl_path[] = {
1477 { .procname = "net", .ctl_name = CTL_NET, },
1478 { .procname = "ipv4", .ctl_name = NET_IPV4, },
1479 { .procname = "conf", .ctl_name = NET_IPV4_CONF, },
1480 { /* to be set */ },
1481 { },
1482 };
1483
1509 t = kmemdup(&devinet_sysctl, sizeof(*t), GFP_KERNEL); 1484 t = kmemdup(&devinet_sysctl, sizeof(*t), GFP_KERNEL);
1510 if (!t) 1485 if (!t)
1511 goto out; 1486 goto out;
@@ -1515,24 +1490,20 @@ static void __devinet_sysctl_register(char *dev_name, int ctl_name,
1515 t->devinet_vars[i].extra1 = p; 1490 t->devinet_vars[i].extra1 = p;
1516 } 1491 }
1517 1492
1518 t->devinet_dev[0].ctl_name = ctl_name;
1519
1520 /* 1493 /*
1521 * Make a copy of dev_name, because '.procname' is regarded as const 1494 * Make a copy of dev_name, because '.procname' is regarded as const
1522 * by sysctl and we wouldn't want anyone to change it under our feet 1495 * by sysctl and we wouldn't want anyone to change it under our feet
1523 * (see SIOCSIFNAME). 1496 * (see SIOCSIFNAME).
1524 */ 1497 */
1525 dev_name = kstrdup(dev_name, GFP_KERNEL); 1498 t->dev_name = kstrdup(dev_name, GFP_KERNEL);
1526 if (!dev_name) 1499 if (!t->dev_name)
1527 goto free; 1500 goto free;
1528 1501
1529 t->devinet_dev[0].procname = dev_name; 1502 devinet_ctl_path[DEVINET_CTL_PATH_DEV].procname = t->dev_name;
1530 t->devinet_dev[0].child = t->devinet_vars; 1503 devinet_ctl_path[DEVINET_CTL_PATH_DEV].ctl_name = ctl_name;
1531 t->devinet_conf_dir[0].child = t->devinet_dev;
1532 t->devinet_proto_dir[0].child = t->devinet_conf_dir;
1533 t->devinet_root_dir[0].child = t->devinet_proto_dir;
1534 1504
1535 t->sysctl_header = register_sysctl_table(t->devinet_root_dir); 1505 t->sysctl_header = register_sysctl_paths(devinet_ctl_path,
1506 t->devinet_vars);
1536 if (!t->sysctl_header) 1507 if (!t->sysctl_header)
1537 goto free_procname; 1508 goto free_procname;
1538 1509
@@ -1540,7 +1511,7 @@ static void __devinet_sysctl_register(char *dev_name, int ctl_name,
1540 return; 1511 return;
1541 1512
1542free_procname: 1513free_procname:
1543 kfree(dev_name); 1514 kfree(t->dev_name);
1544free: 1515free:
1545 kfree(t); 1516 kfree(t);
1546out: 1517out:
@@ -1559,7 +1530,7 @@ static void devinet_sysctl_unregister(struct ipv4_devconf *p)
1559 struct devinet_sysctl_table *t = p->sysctl; 1530 struct devinet_sysctl_table *t = p->sysctl;
1560 p->sysctl = NULL; 1531 p->sysctl = NULL;
1561 unregister_sysctl_table(t->sysctl_header); 1532 unregister_sysctl_table(t->sysctl_header);
1562 kfree(t->devinet_dev[0].procname); 1533 kfree(t->dev_name);
1563 kfree(t); 1534 kfree(t);
1564 } 1535 }
1565} 1536}