aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/cpuset.c
diff options
context:
space:
mode:
Diffstat (limited to 'kernel/cpuset.c')
-rw-r--r--kernel/cpuset.c160
1 files changed, 83 insertions, 77 deletions
diff --git a/kernel/cpuset.c b/kernel/cpuset.c
index 48a976c52cf5..832004935ca7 100644
--- a/kernel/cpuset.c
+++ b/kernel/cpuset.c
@@ -1023,19 +1023,6 @@ int current_cpuset_is_being_rebound(void)
1023 return task_cs(current) == cpuset_being_rebound; 1023 return task_cs(current) == cpuset_being_rebound;
1024} 1024}
1025 1025
1026/*
1027 * Call with cgroup_mutex held.
1028 */
1029
1030static int update_memory_pressure_enabled(struct cpuset *cs, char *buf)
1031{
1032 if (simple_strtoul(buf, NULL, 10) != 0)
1033 cpuset_memory_pressure_enabled = 1;
1034 else
1035 cpuset_memory_pressure_enabled = 0;
1036 return 0;
1037}
1038
1039static int update_relax_domain_level(struct cpuset *cs, char *buf) 1026static int update_relax_domain_level(struct cpuset *cs, char *buf)
1040{ 1027{
1041 int val = simple_strtol(buf, NULL, 10); 1028 int val = simple_strtol(buf, NULL, 10);
@@ -1063,15 +1050,13 @@ static int update_relax_domain_level(struct cpuset *cs, char *buf)
1063 * Call with cgroup_mutex held. 1050 * Call with cgroup_mutex held.
1064 */ 1051 */
1065 1052
1066static int update_flag(cpuset_flagbits_t bit, struct cpuset *cs, char *buf) 1053static int update_flag(cpuset_flagbits_t bit, struct cpuset *cs,
1054 int turning_on)
1067{ 1055{
1068 int turning_on;
1069 struct cpuset trialcs; 1056 struct cpuset trialcs;
1070 int err; 1057 int err;
1071 int cpus_nonempty, balance_flag_changed; 1058 int cpus_nonempty, balance_flag_changed;
1072 1059
1073 turning_on = (simple_strtoul(buf, NULL, 10) != 0);
1074
1075 trialcs = *cs; 1060 trialcs = *cs;
1076 if (turning_on) 1061 if (turning_on)
1077 set_bit(bit, &trialcs.flags); 1062 set_bit(bit, &trialcs.flags);
@@ -1289,46 +1274,68 @@ static ssize_t cpuset_common_file_write(struct cgroup *cont,
1289 case FILE_MEMLIST: 1274 case FILE_MEMLIST:
1290 retval = update_nodemask(cs, buffer); 1275 retval = update_nodemask(cs, buffer);
1291 break; 1276 break;
1277 case FILE_SCHED_RELAX_DOMAIN_LEVEL:
1278 retval = update_relax_domain_level(cs, buffer);
1279 break;
1280 default:
1281 retval = -EINVAL;
1282 goto out2;
1283 }
1284
1285 if (retval == 0)
1286 retval = nbytes;
1287out2:
1288 cgroup_unlock();
1289out1:
1290 kfree(buffer);
1291 return retval;
1292}
1293
1294static int cpuset_write_u64(struct cgroup *cgrp, struct cftype *cft, u64 val)
1295{
1296 int retval = 0;
1297 struct cpuset *cs = cgroup_cs(cgrp);
1298 cpuset_filetype_t type = cft->private;
1299
1300 cgroup_lock();
1301
1302 if (cgroup_is_removed(cgrp)) {
1303 cgroup_unlock();
1304 return -ENODEV;
1305 }
1306
1307 switch (type) {
1292 case FILE_CPU_EXCLUSIVE: 1308 case FILE_CPU_EXCLUSIVE:
1293 retval = update_flag(CS_CPU_EXCLUSIVE, cs, buffer); 1309 retval = update_flag(CS_CPU_EXCLUSIVE, cs, val);
1294 break; 1310 break;
1295 case FILE_MEM_EXCLUSIVE: 1311 case FILE_MEM_EXCLUSIVE:
1296 retval = update_flag(CS_MEM_EXCLUSIVE, cs, buffer); 1312 retval = update_flag(CS_MEM_EXCLUSIVE, cs, val);
1297 break; 1313 break;
1298 case FILE_SCHED_LOAD_BALANCE: 1314 case FILE_SCHED_LOAD_BALANCE:
1299 retval = update_flag(CS_SCHED_LOAD_BALANCE, cs, buffer); 1315 retval = update_flag(CS_SCHED_LOAD_BALANCE, cs, val);
1300 break;
1301 case FILE_SCHED_RELAX_DOMAIN_LEVEL:
1302 retval = update_relax_domain_level(cs, buffer);
1303 break; 1316 break;
1304 case FILE_MEMORY_MIGRATE: 1317 case FILE_MEMORY_MIGRATE:
1305 retval = update_flag(CS_MEMORY_MIGRATE, cs, buffer); 1318 retval = update_flag(CS_MEMORY_MIGRATE, cs, val);
1306 break; 1319 break;
1307 case FILE_MEMORY_PRESSURE_ENABLED: 1320 case FILE_MEMORY_PRESSURE_ENABLED:
1308 retval = update_memory_pressure_enabled(cs, buffer); 1321 cpuset_memory_pressure_enabled = !!val;
1309 break; 1322 break;
1310 case FILE_MEMORY_PRESSURE: 1323 case FILE_MEMORY_PRESSURE:
1311 retval = -EACCES; 1324 retval = -EACCES;
1312 break; 1325 break;
1313 case FILE_SPREAD_PAGE: 1326 case FILE_SPREAD_PAGE:
1314 retval = update_flag(CS_SPREAD_PAGE, cs, buffer); 1327 retval = update_flag(CS_SPREAD_PAGE, cs, val);
1315 cs->mems_generation = cpuset_mems_generation++; 1328 cs->mems_generation = cpuset_mems_generation++;
1316 break; 1329 break;
1317 case FILE_SPREAD_SLAB: 1330 case FILE_SPREAD_SLAB:
1318 retval = update_flag(CS_SPREAD_SLAB, cs, buffer); 1331 retval = update_flag(CS_SPREAD_SLAB, cs, val);
1319 cs->mems_generation = cpuset_mems_generation++; 1332 cs->mems_generation = cpuset_mems_generation++;
1320 break; 1333 break;
1321 default: 1334 default:
1322 retval = -EINVAL; 1335 retval = -EINVAL;
1323 goto out2; 1336 break;
1324 } 1337 }
1325
1326 if (retval == 0)
1327 retval = nbytes;
1328out2:
1329 cgroup_unlock(); 1338 cgroup_unlock();
1330out1:
1331 kfree(buffer);
1332 return retval; 1339 return retval;
1333} 1340}
1334 1341
@@ -1390,33 +1397,9 @@ static ssize_t cpuset_common_file_read(struct cgroup *cont,
1390 case FILE_MEMLIST: 1397 case FILE_MEMLIST:
1391 s += cpuset_sprintf_memlist(s, cs); 1398 s += cpuset_sprintf_memlist(s, cs);
1392 break; 1399 break;
1393 case FILE_CPU_EXCLUSIVE:
1394 *s++ = is_cpu_exclusive(cs) ? '1' : '0';
1395 break;
1396 case FILE_MEM_EXCLUSIVE:
1397 *s++ = is_mem_exclusive(cs) ? '1' : '0';
1398 break;
1399 case FILE_SCHED_LOAD_BALANCE:
1400 *s++ = is_sched_load_balance(cs) ? '1' : '0';
1401 break;
1402 case FILE_SCHED_RELAX_DOMAIN_LEVEL: 1400 case FILE_SCHED_RELAX_DOMAIN_LEVEL:
1403 s += sprintf(s, "%d", cs->relax_domain_level); 1401 s += sprintf(s, "%d", cs->relax_domain_level);
1404 break; 1402 break;
1405 case FILE_MEMORY_MIGRATE:
1406 *s++ = is_memory_migrate(cs) ? '1' : '0';
1407 break;
1408 case FILE_MEMORY_PRESSURE_ENABLED:
1409 *s++ = cpuset_memory_pressure_enabled ? '1' : '0';
1410 break;
1411 case FILE_MEMORY_PRESSURE:
1412 s += sprintf(s, "%d", fmeter_getrate(&cs->fmeter));
1413 break;
1414 case FILE_SPREAD_PAGE:
1415 *s++ = is_spread_page(cs) ? '1' : '0';
1416 break;
1417 case FILE_SPREAD_SLAB:
1418 *s++ = is_spread_slab(cs) ? '1' : '0';
1419 break;
1420 default: 1403 default:
1421 retval = -EINVAL; 1404 retval = -EINVAL;
1422 goto out; 1405 goto out;
@@ -1429,8 +1412,31 @@ out:
1429 return retval; 1412 return retval;
1430} 1413}
1431 1414
1432 1415static u64 cpuset_read_u64(struct cgroup *cont, struct cftype *cft)
1433 1416{
1417 struct cpuset *cs = cgroup_cs(cont);
1418 cpuset_filetype_t type = cft->private;
1419 switch (type) {
1420 case FILE_CPU_EXCLUSIVE:
1421 return is_cpu_exclusive(cs);
1422 case FILE_MEM_EXCLUSIVE:
1423 return is_mem_exclusive(cs);
1424 case FILE_SCHED_LOAD_BALANCE:
1425 return is_sched_load_balance(cs);
1426 case FILE_MEMORY_MIGRATE:
1427 return is_memory_migrate(cs);
1428 case FILE_MEMORY_PRESSURE_ENABLED:
1429 return cpuset_memory_pressure_enabled;
1430 case FILE_MEMORY_PRESSURE:
1431 return fmeter_getrate(&cs->fmeter);
1432 case FILE_SPREAD_PAGE:
1433 return is_spread_page(cs);
1434 case FILE_SPREAD_SLAB:
1435 return is_spread_slab(cs);
1436 default:
1437 BUG();
1438 }
1439}
1434 1440
1435 1441
1436/* 1442/*
@@ -1453,22 +1459,22 @@ static struct cftype cft_mems = {
1453 1459
1454static struct cftype cft_cpu_exclusive = { 1460static struct cftype cft_cpu_exclusive = {
1455 .name = "cpu_exclusive", 1461 .name = "cpu_exclusive",
1456 .read = cpuset_common_file_read, 1462 .read_u64 = cpuset_read_u64,
1457 .write = cpuset_common_file_write, 1463 .write_u64 = cpuset_write_u64,
1458 .private = FILE_CPU_EXCLUSIVE, 1464 .private = FILE_CPU_EXCLUSIVE,
1459}; 1465};
1460 1466
1461static struct cftype cft_mem_exclusive = { 1467static struct cftype cft_mem_exclusive = {
1462 .name = "mem_exclusive", 1468 .name = "mem_exclusive",
1463 .read = cpuset_common_file_read, 1469 .read_u64 = cpuset_read_u64,
1464 .write = cpuset_common_file_write, 1470 .write_u64 = cpuset_write_u64,
1465 .private = FILE_MEM_EXCLUSIVE, 1471 .private = FILE_MEM_EXCLUSIVE,
1466}; 1472};
1467 1473
1468static struct cftype cft_sched_load_balance = { 1474static struct cftype cft_sched_load_balance = {
1469 .name = "sched_load_balance", 1475 .name = "sched_load_balance",
1470 .read = cpuset_common_file_read, 1476 .read_u64 = cpuset_read_u64,
1471 .write = cpuset_common_file_write, 1477 .write_u64 = cpuset_write_u64,
1472 .private = FILE_SCHED_LOAD_BALANCE, 1478 .private = FILE_SCHED_LOAD_BALANCE,
1473}; 1479};
1474 1480
@@ -1481,36 +1487,36 @@ static struct cftype cft_sched_relax_domain_level = {
1481 1487
1482static struct cftype cft_memory_migrate = { 1488static struct cftype cft_memory_migrate = {
1483 .name = "memory_migrate", 1489 .name = "memory_migrate",
1484 .read = cpuset_common_file_read, 1490 .read_u64 = cpuset_read_u64,
1485 .write = cpuset_common_file_write, 1491 .write_u64 = cpuset_write_u64,
1486 .private = FILE_MEMORY_MIGRATE, 1492 .private = FILE_MEMORY_MIGRATE,
1487}; 1493};
1488 1494
1489static struct cftype cft_memory_pressure_enabled = { 1495static struct cftype cft_memory_pressure_enabled = {
1490 .name = "memory_pressure_enabled", 1496 .name = "memory_pressure_enabled",
1491 .read = cpuset_common_file_read, 1497 .read_u64 = cpuset_read_u64,
1492 .write = cpuset_common_file_write, 1498 .write_u64 = cpuset_write_u64,
1493 .private = FILE_MEMORY_PRESSURE_ENABLED, 1499 .private = FILE_MEMORY_PRESSURE_ENABLED,
1494}; 1500};
1495 1501
1496static struct cftype cft_memory_pressure = { 1502static struct cftype cft_memory_pressure = {
1497 .name = "memory_pressure", 1503 .name = "memory_pressure",
1498 .read = cpuset_common_file_read, 1504 .read_u64 = cpuset_read_u64,
1499 .write = cpuset_common_file_write, 1505 .write_u64 = cpuset_write_u64,
1500 .private = FILE_MEMORY_PRESSURE, 1506 .private = FILE_MEMORY_PRESSURE,
1501}; 1507};
1502 1508
1503static struct cftype cft_spread_page = { 1509static struct cftype cft_spread_page = {
1504 .name = "memory_spread_page", 1510 .name = "memory_spread_page",
1505 .read = cpuset_common_file_read, 1511 .read_u64 = cpuset_read_u64,
1506 .write = cpuset_common_file_write, 1512 .write_u64 = cpuset_write_u64,
1507 .private = FILE_SPREAD_PAGE, 1513 .private = FILE_SPREAD_PAGE,
1508}; 1514};
1509 1515
1510static struct cftype cft_spread_slab = { 1516static struct cftype cft_spread_slab = {
1511 .name = "memory_spread_slab", 1517 .name = "memory_spread_slab",
1512 .read = cpuset_common_file_read, 1518 .read_u64 = cpuset_read_u64,
1513 .write = cpuset_common_file_write, 1519 .write_u64 = cpuset_write_u64,
1514 .private = FILE_SPREAD_SLAB, 1520 .private = FILE_SPREAD_SLAB,
1515}; 1521};
1516 1522
@@ -1643,7 +1649,7 @@ static void cpuset_destroy(struct cgroup_subsys *ss, struct cgroup *cont)
1643 cpuset_update_task_memory_state(); 1649 cpuset_update_task_memory_state();
1644 1650
1645 if (is_sched_load_balance(cs)) 1651 if (is_sched_load_balance(cs))
1646 update_flag(CS_SCHED_LOAD_BALANCE, cs, "0"); 1652 update_flag(CS_SCHED_LOAD_BALANCE, cs, 0);
1647 1653
1648 number_of_cpusets--; 1654 number_of_cpusets--;
1649 kfree(cs); 1655 kfree(cs);