Home | History | Annotate | Download | only in include
      1 /*
      2  *  Copyright 2018 Google, Inc
      3  *
      4  *  Licensed under the Apache License, Version 2.0 (the "License");
      5  *  you may not use this file except in compliance with the License.
      6  *  You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  *  Unless required by applicable law or agreed to in writing, software
     11  *  distributed under the License is distributed on an "AS IS" BASIS,
     12  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  *  See the License for the specific language governing permissions and
     14  *  limitations under the License.
     15  */
     16 
     17 #ifndef _LMKD_H_
     18 #define _LMKD_H_
     19 
     20 #include <arpa/inet.h>
     21 #include <sys/cdefs.h>
     22 #include <sys/types.h>
     23 
     24 __BEGIN_DECLS
     25 
     26 /*
     27  * Supported LMKD commands
     28  */
     29 enum lmk_cmd {
     30     LMK_TARGET = 0,  /* Associate minfree with oom_adj_score */
     31     LMK_PROCPRIO,    /* Register a process and set its oom_adj_score */
     32     LMK_PROCREMOVE,  /* Unregister a process */
     33 };
     34 
     35 /*
     36  * Max number of targets in LMK_TARGET command.
     37  */
     38 #define MAX_TARGETS 6
     39 
     40 /*
     41  * Max packet length in bytes.
     42  * Longest packet is LMK_TARGET followed by MAX_TARGETS
     43  * of minfree and oom_adj_score values
     44  */
     45 #define CTRL_PACKET_MAX_SIZE (sizeof(int) * (MAX_TARGETS * 2 + 1))
     46 
     47 /* LMKD packet - first int is lmk_cmd followed by payload */
     48 typedef int LMKD_CTRL_PACKET[CTRL_PACKET_MAX_SIZE / sizeof(int)];
     49 
     50 /* Get LMKD packet command */
     51 inline enum lmk_cmd lmkd_pack_get_cmd(LMKD_CTRL_PACKET pack) {
     52     return (enum lmk_cmd)ntohl(pack[0]);
     53 }
     54 
     55 /* LMK_TARGET packet payload */
     56 struct lmk_target {
     57     int minfree;
     58     int oom_adj_score;
     59 };
     60 
     61 /*
     62  * For LMK_TARGET packet get target_idx-th payload.
     63  * Warning: no checks performed, caller should ensure valid parameters.
     64  */
     65 inline void lmkd_pack_get_target(LMKD_CTRL_PACKET packet,
     66                                  int target_idx, struct lmk_target *target) {
     67     target->minfree = ntohl(packet[target_idx * 2 + 1]);
     68     target->oom_adj_score = ntohl(packet[target_idx * 2 + 2]);
     69 }
     70 
     71 /*
     72  * Prepare LMK_TARGET packet and return packet size in bytes.
     73  * Warning: no checks performed, caller should ensure valid parameters.
     74  */
     75 inline size_t lmkd_pack_set_target(LMKD_CTRL_PACKET packet,
     76                                    struct lmk_target *targets,
     77                                    size_t target_cnt) {
     78     int idx = 0;
     79     packet[idx++] = htonl(LMK_TARGET);
     80     while (target_cnt) {
     81         packet[idx++] = htonl(targets->minfree);
     82         packet[idx++] = htonl(targets->oom_adj_score);
     83         targets++;
     84         target_cnt--;
     85     }
     86     return idx * sizeof(int);
     87 }
     88 
     89 /* LMK_PROCPRIO packet payload */
     90 struct lmk_procprio {
     91     pid_t pid;
     92     uid_t uid;
     93     int oomadj;
     94 };
     95 
     96 /*
     97  * For LMK_PROCPRIO packet get its payload.
     98  * Warning: no checks performed, caller should ensure valid parameters.
     99  */
    100 inline void lmkd_pack_get_procprio(LMKD_CTRL_PACKET packet,
    101                                    struct lmk_procprio *params) {
    102     params->pid = (pid_t)ntohl(packet[1]);
    103     params->uid = (uid_t)ntohl(packet[2]);
    104     params->oomadj = ntohl(packet[3]);
    105 }
    106 
    107 /*
    108  * Prepare LMK_PROCPRIO packet and return packet size in bytes.
    109  * Warning: no checks performed, caller should ensure valid parameters.
    110  */
    111 inline size_t lmkd_pack_set_procprio(LMKD_CTRL_PACKET packet,
    112                                    struct lmk_procprio *params) {
    113     packet[0] = htonl(LMK_PROCPRIO);
    114     packet[1] = htonl(params->pid);
    115     packet[2] = htonl(params->uid);
    116     packet[3] = htonl(params->oomadj);
    117     return 4 * sizeof(int);
    118 }
    119 
    120 /* LMK_PROCREMOVE packet payload */
    121 struct lmk_procremove {
    122     pid_t pid;
    123 };
    124 
    125 /*
    126  * For LMK_PROCREMOVE packet get its payload.
    127  * Warning: no checks performed, caller should ensure valid parameters.
    128  */
    129 inline void lmkd_pack_get_procremove(LMKD_CTRL_PACKET packet,
    130                                    struct lmk_procremove *params) {
    131     params->pid = (pid_t)ntohl(packet[1]);
    132 }
    133 
    134 /*
    135  * Prepare LMK_PROCREMOVE packet and return packet size in bytes.
    136  * Warning: no checks performed, caller should ensure valid parameters.
    137  */
    138 inline size_t lmkd_pack_set_procremove(LMKD_CTRL_PACKET packet,
    139                                    struct lmk_procprio *params) {
    140     packet[0] = htonl(LMK_PROCREMOVE);
    141     packet[1] = htonl(params->pid);
    142     return 2 * sizeof(int);
    143 }
    144 
    145 __END_DECLS
    146 
    147 #endif /* _LMKD_H_ */
    148