lmkd: Introduce liblmkd_utils for communicating with lmkd process
(cherry pick from commit 0f1005180513e880bf7c90a3f2c2bf1a36aa1406) A number of tools and tests require communication with lmkd. In order to avoid code duplication liblmkd_utils implements functions commonly used when interacting with lmkd process. Isolate communication protocol details into lmkd.h Bug: 63631020 Change-Id: Id840983d55b7db60013d52dee0c3187943811822 Merged-In: Id840983d55b7db60013d52dee0c3187943811822 Signed-off-by: Suren Baghdasaryan <surenb@google.com>
This commit is contained in:
parent
c53a16b4c6
commit
a743800b47
15
Android.bp
15
Android.bp
|
|
@ -6,6 +6,7 @@ cc_binary {
|
||||||
"liblog",
|
"liblog",
|
||||||
"libcutils",
|
"libcutils",
|
||||||
],
|
],
|
||||||
|
local_include_dirs: ["include"],
|
||||||
cflags: ["-Werror"],
|
cflags: ["-Werror"],
|
||||||
|
|
||||||
init_rc: ["lmkd.rc"],
|
init_rc: ["lmkd.rc"],
|
||||||
|
|
@ -18,3 +19,17 @@ cc_binary {
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cc_library_static {
|
||||||
|
name: "liblmkd_utils",
|
||||||
|
srcs: ["liblmkd_utils.c"],
|
||||||
|
shared_libs: [
|
||||||
|
"libcutils",
|
||||||
|
],
|
||||||
|
export_include_dirs: ["include"],
|
||||||
|
cppflags: [
|
||||||
|
"-g",
|
||||||
|
"-Wall",
|
||||||
|
"-Werror",
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,54 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2018 Google, Inc
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _LIBLMKD_UTILS_H_
|
||||||
|
#define _LIBLMKD_UTILS_H_
|
||||||
|
|
||||||
|
#include <sys/cdefs.h>
|
||||||
|
#include <sys/types.h>
|
||||||
|
|
||||||
|
#include <lmkd.h>
|
||||||
|
|
||||||
|
__BEGIN_DECLS
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Connects to lmkd process and returns socket handle.
|
||||||
|
* On success returns socket handle.
|
||||||
|
* On error, -1 is returned, and errno is set appropriately.
|
||||||
|
*/
|
||||||
|
int lmkd_connect();
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Registers a process with lmkd and sets its oomadj score.
|
||||||
|
* On success returns 0.
|
||||||
|
* On error, -1 is returned.
|
||||||
|
* In the case of error errno is set appropriately.
|
||||||
|
*/
|
||||||
|
int lmkd_register_proc(int sock, struct lmk_procprio *params);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Creates memcg directory for given process.
|
||||||
|
* On success returns 0.
|
||||||
|
* -1 is returned if path creation failed.
|
||||||
|
* -2 is returned if tasks file open operation failed.
|
||||||
|
* -3 is returned if tasks file write operation failed.
|
||||||
|
* In the case of error errno is set appropriately.
|
||||||
|
*/
|
||||||
|
int create_memcg(uid_t uid, pid_t pid);
|
||||||
|
|
||||||
|
__END_DECLS
|
||||||
|
|
||||||
|
#endif /* _LIBLMKD_UTILS_H_ */
|
||||||
|
|
@ -0,0 +1,147 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2018 Google, Inc
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _LMKD_H_
|
||||||
|
#define _LMKD_H_
|
||||||
|
|
||||||
|
#include <arpa/inet.h>
|
||||||
|
#include <sys/cdefs.h>
|
||||||
|
#include <sys/types.h>
|
||||||
|
|
||||||
|
__BEGIN_DECLS
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Supported LMKD commands
|
||||||
|
*/
|
||||||
|
enum lmk_cmd {
|
||||||
|
LMK_TARGET = 0, /* Associate minfree with oom_adj_score */
|
||||||
|
LMK_PROCPRIO, /* Register a process and set its oom_adj_score */
|
||||||
|
LMK_PROCREMOVE, /* Unregister a process */
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Max number of targets in LMK_TARGET command.
|
||||||
|
*/
|
||||||
|
#define MAX_TARGETS 6
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Max packet length in bytes.
|
||||||
|
* Longest packet is LMK_TARGET followed by MAX_TARGETS
|
||||||
|
* of minfree and oom_adj_score values
|
||||||
|
*/
|
||||||
|
#define CTRL_PACKET_MAX_SIZE (sizeof(int) * (MAX_TARGETS * 2 + 1))
|
||||||
|
|
||||||
|
/* LMKD packet - first int is lmk_cmd followed by payload */
|
||||||
|
typedef int LMKD_CTRL_PACKET[CTRL_PACKET_MAX_SIZE / sizeof(int)];
|
||||||
|
|
||||||
|
/* Get LMKD packet command */
|
||||||
|
inline enum lmk_cmd lmkd_pack_get_cmd(LMKD_CTRL_PACKET pack) {
|
||||||
|
return (enum lmk_cmd)ntohl(pack[0]);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* LMK_TARGET packet payload */
|
||||||
|
struct lmk_target {
|
||||||
|
int minfree;
|
||||||
|
int oom_adj_score;
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
* For LMK_TARGET packet get target_idx-th payload.
|
||||||
|
* Warning: no checks performed, caller should ensure valid parameters.
|
||||||
|
*/
|
||||||
|
inline void lmkd_pack_get_target(LMKD_CTRL_PACKET packet,
|
||||||
|
int target_idx, struct lmk_target *target) {
|
||||||
|
target->minfree = ntohl(packet[target_idx * 2 + 1]);
|
||||||
|
target->oom_adj_score = ntohl(packet[target_idx * 2 + 2]);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Prepare LMK_TARGET packet and return packet size in bytes.
|
||||||
|
* Warning: no checks performed, caller should ensure valid parameters.
|
||||||
|
*/
|
||||||
|
inline size_t lmkd_pack_set_target(LMKD_CTRL_PACKET packet,
|
||||||
|
struct lmk_target *targets,
|
||||||
|
size_t target_cnt) {
|
||||||
|
int idx = 0;
|
||||||
|
packet[idx++] = htonl(LMK_TARGET);
|
||||||
|
while (target_cnt) {
|
||||||
|
packet[idx++] = htonl(targets->minfree);
|
||||||
|
packet[idx++] = htonl(targets->oom_adj_score);
|
||||||
|
targets++;
|
||||||
|
target_cnt--;
|
||||||
|
}
|
||||||
|
return idx * sizeof(int);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* LMK_PROCPRIO packet payload */
|
||||||
|
struct lmk_procprio {
|
||||||
|
pid_t pid;
|
||||||
|
uid_t uid;
|
||||||
|
int oomadj;
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
* For LMK_PROCPRIO packet get its payload.
|
||||||
|
* Warning: no checks performed, caller should ensure valid parameters.
|
||||||
|
*/
|
||||||
|
inline void lmkd_pack_get_procprio(LMKD_CTRL_PACKET packet,
|
||||||
|
struct lmk_procprio *params) {
|
||||||
|
params->pid = (pid_t)ntohl(packet[1]);
|
||||||
|
params->uid = (uid_t)ntohl(packet[2]);
|
||||||
|
params->oomadj = ntohl(packet[3]);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Prepare LMK_PROCPRIO packet and return packet size in bytes.
|
||||||
|
* Warning: no checks performed, caller should ensure valid parameters.
|
||||||
|
*/
|
||||||
|
inline size_t lmkd_pack_set_procprio(LMKD_CTRL_PACKET packet,
|
||||||
|
struct lmk_procprio *params) {
|
||||||
|
packet[0] = htonl(LMK_PROCPRIO);
|
||||||
|
packet[1] = htonl(params->pid);
|
||||||
|
packet[2] = htonl(params->uid);
|
||||||
|
packet[3] = htonl(params->oomadj);
|
||||||
|
return 4 * sizeof(int);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* LMK_PROCREMOVE packet payload */
|
||||||
|
struct lmk_procremove {
|
||||||
|
pid_t pid;
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
* For LMK_PROCREMOVE packet get its payload.
|
||||||
|
* Warning: no checks performed, caller should ensure valid parameters.
|
||||||
|
*/
|
||||||
|
inline void lmkd_pack_get_procremove(LMKD_CTRL_PACKET packet,
|
||||||
|
struct lmk_procremove *params) {
|
||||||
|
params->pid = (pid_t)ntohl(packet[1]);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Prepare LMK_PROCREMOVE packet and return packet size in bytes.
|
||||||
|
* Warning: no checks performed, caller should ensure valid parameters.
|
||||||
|
*/
|
||||||
|
inline size_t lmkd_pack_set_procremove(LMKD_CTRL_PACKET packet,
|
||||||
|
struct lmk_procprio *params) {
|
||||||
|
packet[0] = htonl(LMK_PROCREMOVE);
|
||||||
|
packet[1] = htonl(params->pid);
|
||||||
|
return 2 * sizeof(int);
|
||||||
|
}
|
||||||
|
|
||||||
|
__END_DECLS
|
||||||
|
|
||||||
|
#endif /* _LMKD_H_ */
|
||||||
|
|
@ -0,0 +1,76 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2018 Google, Inc
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <errno.h>
|
||||||
|
#include <fcntl.h>
|
||||||
|
#include <sys/cdefs.h>
|
||||||
|
#include <sys/stat.h>
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
|
||||||
|
#include <liblmkd_utils.h>
|
||||||
|
#include <cutils/sockets.h>
|
||||||
|
|
||||||
|
int lmkd_connect() {
|
||||||
|
return socket_local_client("lmkd",
|
||||||
|
ANDROID_SOCKET_NAMESPACE_RESERVED,
|
||||||
|
SOCK_SEQPACKET);
|
||||||
|
}
|
||||||
|
|
||||||
|
int lmkd_register_proc(int sock, struct lmk_procprio *params) {
|
||||||
|
LMKD_CTRL_PACKET packet;
|
||||||
|
size_t size;
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
size = lmkd_pack_set_procprio(packet, params);
|
||||||
|
ret = TEMP_FAILURE_RETRY(write(sock, packet, size));
|
||||||
|
|
||||||
|
return (ret < 0) ? -1 : 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int create_memcg(uid_t uid, pid_t pid) {
|
||||||
|
char buf[256];
|
||||||
|
int tasks_file;
|
||||||
|
int written;
|
||||||
|
|
||||||
|
snprintf(buf, sizeof(buf), "/dev/memcg/apps/uid_%u", uid);
|
||||||
|
if (mkdir(buf, S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH) < 0 &&
|
||||||
|
errno != EEXIST) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
snprintf(buf, sizeof(buf), "/dev/memcg/apps/uid_%u/pid_%u", uid, pid);
|
||||||
|
if (mkdir(buf, S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH) < 0 &&
|
||||||
|
errno != EEXIST) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
snprintf(buf, sizeof(buf), "/dev/memcg/apps/uid_%u/pid_%u/tasks", uid, pid);
|
||||||
|
tasks_file = open(buf, O_WRONLY);
|
||||||
|
if (tasks_file < 0) {
|
||||||
|
return -2;
|
||||||
|
}
|
||||||
|
written = snprintf(buf, sizeof(buf), "%u", pid);
|
||||||
|
if (__predict_false(written >= (int)sizeof(buf))) {
|
||||||
|
written = sizeof(buf) - 1;
|
||||||
|
}
|
||||||
|
written = TEMP_FAILURE_RETRY(write(tasks_file, buf, written));
|
||||||
|
close(tasks_file);
|
||||||
|
|
||||||
|
return (written < 0) ? -3 : 0;
|
||||||
|
}
|
||||||
|
|
||||||
100
lmkd.c
100
lmkd.c
|
|
@ -16,7 +16,6 @@
|
||||||
|
|
||||||
#define LOG_TAG "lowmemorykiller"
|
#define LOG_TAG "lowmemorykiller"
|
||||||
|
|
||||||
#include <arpa/inet.h>
|
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <inttypes.h>
|
#include <inttypes.h>
|
||||||
#include <sched.h>
|
#include <sched.h>
|
||||||
|
|
@ -34,6 +33,7 @@
|
||||||
|
|
||||||
#include <cutils/properties.h>
|
#include <cutils/properties.h>
|
||||||
#include <cutils/sockets.h>
|
#include <cutils/sockets.h>
|
||||||
|
#include <lmkd.h>
|
||||||
#include <log/log.h>
|
#include <log/log.h>
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
@ -71,19 +71,6 @@
|
||||||
#define ARRAY_SIZE(x) (sizeof(x) / sizeof(*(x)))
|
#define ARRAY_SIZE(x) (sizeof(x) / sizeof(*(x)))
|
||||||
#define EIGHT_MEGA (1 << 23)
|
#define EIGHT_MEGA (1 << 23)
|
||||||
|
|
||||||
enum lmk_cmd {
|
|
||||||
LMK_TARGET,
|
|
||||||
LMK_PROCPRIO,
|
|
||||||
LMK_PROCREMOVE,
|
|
||||||
};
|
|
||||||
|
|
||||||
#define MAX_TARGETS 6
|
|
||||||
/*
|
|
||||||
* longest is LMK_TARGET followed by MAX_TARGETS each minfree and minkillprio
|
|
||||||
* values
|
|
||||||
*/
|
|
||||||
#define CTRL_PACKET_MAX (sizeof(int) * (MAX_TARGETS * 2 + 1))
|
|
||||||
|
|
||||||
/* default to old in-kernel interface if no memory pressure events */
|
/* default to old in-kernel interface if no memory pressure events */
|
||||||
static int use_inkernel_interface = 1;
|
static int use_inkernel_interface = 1;
|
||||||
static bool has_inkernel_module;
|
static bool has_inkernel_module;
|
||||||
|
|
@ -300,45 +287,49 @@ static void writefilestring(const char *path, char *s) {
|
||||||
close(fd);
|
close(fd);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void cmd_procprio(int pid, int uid, int oomadj) {
|
static void cmd_procprio(LMKD_CTRL_PACKET packet) {
|
||||||
struct proc *procp;
|
struct proc *procp;
|
||||||
char path[80];
|
char path[80];
|
||||||
char val[20];
|
char val[20];
|
||||||
int soft_limit_mult;
|
int soft_limit_mult;
|
||||||
|
struct lmk_procprio params;
|
||||||
|
|
||||||
if (oomadj < OOM_SCORE_ADJ_MIN || oomadj > OOM_SCORE_ADJ_MAX) {
|
lmkd_pack_get_procprio(packet, ¶ms);
|
||||||
ALOGE("Invalid PROCPRIO oomadj argument %d", oomadj);
|
|
||||||
|
if (params.oomadj < OOM_SCORE_ADJ_MIN ||
|
||||||
|
params.oomadj > OOM_SCORE_ADJ_MAX) {
|
||||||
|
ALOGE("Invalid PROCPRIO oomadj argument %d", params.oomadj);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
snprintf(path, sizeof(path), "/proc/%d/oom_score_adj", pid);
|
snprintf(path, sizeof(path), "/proc/%d/oom_score_adj", params.pid);
|
||||||
snprintf(val, sizeof(val), "%d", oomadj);
|
snprintf(val, sizeof(val), "%d", params.oomadj);
|
||||||
writefilestring(path, val);
|
writefilestring(path, val);
|
||||||
|
|
||||||
if (use_inkernel_interface)
|
if (use_inkernel_interface)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (oomadj >= 900) {
|
if (params.oomadj >= 900) {
|
||||||
soft_limit_mult = 0;
|
soft_limit_mult = 0;
|
||||||
} else if (oomadj >= 800) {
|
} else if (params.oomadj >= 800) {
|
||||||
soft_limit_mult = 0;
|
soft_limit_mult = 0;
|
||||||
} else if (oomadj >= 700) {
|
} else if (params.oomadj >= 700) {
|
||||||
soft_limit_mult = 0;
|
soft_limit_mult = 0;
|
||||||
} else if (oomadj >= 600) {
|
} else if (params.oomadj >= 600) {
|
||||||
// Launcher should be perceptible, don't kill it.
|
// Launcher should be perceptible, don't kill it.
|
||||||
oomadj = 200;
|
params.oomadj = 200;
|
||||||
soft_limit_mult = 1;
|
soft_limit_mult = 1;
|
||||||
} else if (oomadj >= 500) {
|
} else if (params.oomadj >= 500) {
|
||||||
soft_limit_mult = 0;
|
soft_limit_mult = 0;
|
||||||
} else if (oomadj >= 400) {
|
} else if (params.oomadj >= 400) {
|
||||||
soft_limit_mult = 0;
|
soft_limit_mult = 0;
|
||||||
} else if (oomadj >= 300) {
|
} else if (params.oomadj >= 300) {
|
||||||
soft_limit_mult = 1;
|
soft_limit_mult = 1;
|
||||||
} else if (oomadj >= 200) {
|
} else if (params.oomadj >= 200) {
|
||||||
soft_limit_mult = 2;
|
soft_limit_mult = 2;
|
||||||
} else if (oomadj >= 100) {
|
} else if (params.oomadj >= 100) {
|
||||||
soft_limit_mult = 10;
|
soft_limit_mult = 10;
|
||||||
} else if (oomadj >= 0) {
|
} else if (params.oomadj >= 0) {
|
||||||
soft_limit_mult = 20;
|
soft_limit_mult = 20;
|
||||||
} else {
|
} else {
|
||||||
// Persistent processes will have a large
|
// Persistent processes will have a large
|
||||||
|
|
@ -346,11 +337,13 @@ static void cmd_procprio(int pid, int uid, int oomadj) {
|
||||||
soft_limit_mult = 64;
|
soft_limit_mult = 64;
|
||||||
}
|
}
|
||||||
|
|
||||||
snprintf(path, sizeof(path), "/dev/memcg/apps/uid_%d/pid_%d/memory.soft_limit_in_bytes", uid, pid);
|
snprintf(path, sizeof(path),
|
||||||
|
"/dev/memcg/apps/uid_%d/pid_%d/memory.soft_limit_in_bytes",
|
||||||
|
params.uid, params.pid);
|
||||||
snprintf(val, sizeof(val), "%d", soft_limit_mult * EIGHT_MEGA);
|
snprintf(val, sizeof(val), "%d", soft_limit_mult * EIGHT_MEGA);
|
||||||
writefilestring(path, val);
|
writefilestring(path, val);
|
||||||
|
|
||||||
procp = pid_lookup(pid);
|
procp = pid_lookup(params.pid);
|
||||||
if (!procp) {
|
if (!procp) {
|
||||||
procp = malloc(sizeof(struct proc));
|
procp = malloc(sizeof(struct proc));
|
||||||
if (!procp) {
|
if (!procp) {
|
||||||
|
|
@ -358,33 +351,38 @@ static void cmd_procprio(int pid, int uid, int oomadj) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
procp->pid = pid;
|
procp->pid = params.pid;
|
||||||
procp->uid = uid;
|
procp->uid = params.uid;
|
||||||
procp->oomadj = oomadj;
|
procp->oomadj = params.oomadj;
|
||||||
proc_insert(procp);
|
proc_insert(procp);
|
||||||
} else {
|
} else {
|
||||||
proc_unslot(procp);
|
proc_unslot(procp);
|
||||||
procp->oomadj = oomadj;
|
procp->oomadj = params.oomadj;
|
||||||
proc_slot(procp);
|
proc_slot(procp);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void cmd_procremove(int pid) {
|
static void cmd_procremove(LMKD_CTRL_PACKET packet) {
|
||||||
|
struct lmk_procremove params;
|
||||||
|
|
||||||
if (use_inkernel_interface)
|
if (use_inkernel_interface)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
pid_remove(pid);
|
lmkd_pack_get_procremove(packet, ¶ms);
|
||||||
|
pid_remove(params.pid);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void cmd_target(int ntargets, int *params) {
|
static void cmd_target(int ntargets, LMKD_CTRL_PACKET packet) {
|
||||||
int i;
|
int i;
|
||||||
|
struct lmk_target target;
|
||||||
|
|
||||||
if (ntargets > (int)ARRAY_SIZE(lowmem_adj))
|
if (ntargets > (int)ARRAY_SIZE(lowmem_adj))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
for (i = 0; i < ntargets; i++) {
|
for (i = 0; i < ntargets; i++) {
|
||||||
lowmem_minfree[i] = ntohl(*params++);
|
lmkd_pack_get_target(packet, i, &target);
|
||||||
lowmem_adj[i] = ntohl(*params++);
|
lowmem_minfree[i] = target.minfree;
|
||||||
|
lowmem_adj[i] = target.oom_adj_score;
|
||||||
}
|
}
|
||||||
|
|
||||||
lowmem_targets_size = ntargets;
|
lowmem_targets_size = ntargets;
|
||||||
|
|
@ -445,38 +443,42 @@ static int ctrl_data_read(int dsock_idx, char *buf, size_t bufsz) {
|
||||||
}
|
}
|
||||||
|
|
||||||
static void ctrl_command_handler(int dsock_idx) {
|
static void ctrl_command_handler(int dsock_idx) {
|
||||||
int ibuf[CTRL_PACKET_MAX / sizeof(int)];
|
LMKD_CTRL_PACKET packet;
|
||||||
int len;
|
int len;
|
||||||
int cmd = -1;
|
enum lmk_cmd cmd;
|
||||||
int nargs;
|
int nargs;
|
||||||
int targets;
|
int targets;
|
||||||
|
|
||||||
len = ctrl_data_read(dsock_idx, (char *)ibuf, CTRL_PACKET_MAX);
|
len = ctrl_data_read(dsock_idx, (char *)packet, CTRL_PACKET_MAX_SIZE);
|
||||||
if (len <= 0)
|
if (len <= 0)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
if (len < (int)sizeof(int)) {
|
||||||
|
ALOGE("Wrong control socket read length len=%d", len);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
cmd = lmkd_pack_get_cmd(packet);
|
||||||
nargs = len / sizeof(int) - 1;
|
nargs = len / sizeof(int) - 1;
|
||||||
if (nargs < 0)
|
if (nargs < 0)
|
||||||
goto wronglen;
|
goto wronglen;
|
||||||
|
|
||||||
cmd = ntohl(ibuf[0]);
|
|
||||||
|
|
||||||
switch(cmd) {
|
switch(cmd) {
|
||||||
case LMK_TARGET:
|
case LMK_TARGET:
|
||||||
targets = nargs / 2;
|
targets = nargs / 2;
|
||||||
if (nargs & 0x1 || targets > (int)ARRAY_SIZE(lowmem_adj))
|
if (nargs & 0x1 || targets > (int)ARRAY_SIZE(lowmem_adj))
|
||||||
goto wronglen;
|
goto wronglen;
|
||||||
cmd_target(targets, &ibuf[1]);
|
cmd_target(targets, packet);
|
||||||
break;
|
break;
|
||||||
case LMK_PROCPRIO:
|
case LMK_PROCPRIO:
|
||||||
if (nargs != 3)
|
if (nargs != 3)
|
||||||
goto wronglen;
|
goto wronglen;
|
||||||
cmd_procprio(ntohl(ibuf[1]), ntohl(ibuf[2]), ntohl(ibuf[3]));
|
cmd_procprio(packet);
|
||||||
break;
|
break;
|
||||||
case LMK_PROCREMOVE:
|
case LMK_PROCREMOVE:
|
||||||
if (nargs != 1)
|
if (nargs != 1)
|
||||||
goto wronglen;
|
goto wronglen;
|
||||||
cmd_procremove(ntohl(ibuf[1]));
|
cmd_procremove(packet);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
ALOGE("Received unknown command code %d", cmd);
|
ALOGE("Received unknown command code %d", cmd);
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue