1 /*- 2 * Copyright (c) 2014 Gleb Kurtsou <gleb@FreeBSD.org> 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 14 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 15 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 16 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 17 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 18 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 19 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 20 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 21 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 22 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 23 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 24 * SUCH DAMAGE. 25 * 26 * $FreeBSD$ 27 */ 28 29 #include <sys/cdefs.h> 30 __FBSDID("$FreeBSD$"); 31 32 #include <sys/param.h> 33 #include <sys/user.h> 34 #include <sys/socket.h> 35 #include <string.h> 36 37 #include "libprocstat.h" 38 39 #define SPECNAMELEN_COMPAT12 63 40 41 struct freebsd11_ptsstat { 42 uint32_t dev; 43 char devname[SPECNAMELEN_COMPAT12 + 1]; 44 }; 45 46 struct freebsd11_vnstat { 47 uint64_t vn_fileid; 48 uint64_t vn_size; 49 char *vn_mntdir; 50 uint32_t vn_dev; 51 uint32_t vn_fsid; 52 int vn_type; 53 uint16_t vn_mode; 54 char vn_devname[SPECNAMELEN_COMPAT12 + 1]; 55 }; 56 struct freebsd11_semstat { 57 uint32_t value; 58 uint16_t mode; 59 }; 60 struct freebsd11_shmstat { 61 uint64_t size; 62 uint16_t mode; 63 }; 64 65 struct freebsd11_sockstat { 66 uint64_t inp_ppcb; 67 uint64_t so_addr; 68 uint64_t so_pcb; 69 uint64_t unp_conn; 70 int dom_family; 71 int proto; 72 int so_rcv_sb_state; 73 int so_snd_sb_state; 74 struct sockaddr_storage sa_local; /* Socket address. */ 75 struct sockaddr_storage sa_peer; /* Peer address. */ 76 int type; 77 char dname[32]; 78 }; 79 80 struct freebsd12_vnstat { 81 uint64_t vn_fileid; 82 uint64_t vn_size; 83 uint64_t vn_dev; 84 uint64_t vn_fsid; 85 char *vn_mntdir; 86 int vn_type; 87 uint16_t vn_mode; 88 char vn_devname[SPECNAMELEN_COMPAT12 + 1]; 89 }; 90 struct freebsd12_ptsstat { 91 uint64_t dev; 92 char devname[SPECNAMELEN_COMPAT12 + 1]; 93 }; 94 95 int freebsd11_procstat_get_pts_info(struct procstat *procstat, 96 struct filestat *fst, struct freebsd11_ptsstat *pts, char *errbuf); 97 int freebsd12_procstat_get_pts_info(struct procstat *procstat, 98 struct filestat *fst, struct freebsd12_ptsstat *pts_compat, char *errbuf); 99 int freebsd11_procstat_get_sem_info(struct procstat *procstat, 100 struct filestat *fst, struct freebsd11_semstat *sem, char *errbuf); 101 int freebsd11_procstat_get_shm_info(struct procstat *procstat, 102 struct filestat *fst, struct freebsd11_shmstat *shm, char *errbuf); 103 int freebsd11_procstat_get_socket_info(struct procstat *procstat, 104 struct filestat *fst, struct freebsd11_sockstat *sock, char *errbuf); 105 int freebsd11_procstat_get_vnode_info(struct procstat *procstat, 106 struct filestat *fst, struct freebsd11_vnstat *vn, char *errbuf); 107 int freebsd12_procstat_get_vnode_info(struct procstat *procstat, 108 struct filestat *fst, struct freebsd12_vnstat *vn_compat, char *errbuf); 109 110 static const char trunc_name[] = "<TRUNCATED>"; 111 112 int 113 freebsd11_procstat_get_pts_info(struct procstat *procstat, 114 struct filestat *fst, struct freebsd11_ptsstat *pts_compat, char *errbuf) 115 { 116 struct ptsstat pts; 117 int r; 118 119 r = procstat_get_pts_info(procstat, fst, &pts, errbuf); 120 if (r != 0) 121 return (r); 122 pts_compat->dev = pts.dev; 123 if (strlen(pts.devname) >= sizeof(pts_compat->devname)) 124 strcpy(pts_compat->devname, trunc_name); 125 else 126 memcpy(pts_compat->devname, pts.devname, 127 sizeof(pts_compat->devname)); 128 return (0); 129 } 130 131 int 132 freebsd12_procstat_get_pts_info(struct procstat *procstat, 133 struct filestat *fst, struct freebsd12_ptsstat *pts_compat, char *errbuf) 134 { 135 struct ptsstat pts; 136 int r; 137 138 r = procstat_get_pts_info(procstat, fst, &pts, errbuf); 139 if (r != 0) 140 return (r); 141 pts_compat->dev = pts.dev; 142 if (strlen(pts.devname) >= sizeof(pts_compat->devname)) 143 strcpy(pts_compat->devname, trunc_name); 144 else 145 memcpy(pts_compat->devname, pts.devname, 146 sizeof(pts_compat->devname)); 147 return (0); 148 } 149 150 int 151 freebsd11_procstat_get_sem_info(struct procstat *procstat, 152 struct filestat *fst, struct freebsd11_semstat *sem_compat, char *errbuf) 153 { 154 struct semstat sem; 155 int r; 156 157 r = procstat_get_sem_info(procstat, fst, &sem, errbuf); 158 if (r != 0) 159 return (r); 160 sem_compat->value = sem.value; 161 sem_compat->mode = sem.mode; 162 return (0); 163 } 164 165 int 166 freebsd11_procstat_get_shm_info(struct procstat *procstat, 167 struct filestat *fst, struct freebsd11_shmstat *shm_compat, char *errbuf) 168 { 169 struct shmstat shm; 170 int r; 171 172 r = procstat_get_shm_info(procstat, fst, &shm, errbuf); 173 if (r != 0) 174 return (r); 175 shm_compat->size = shm.size; 176 shm_compat->mode = shm.mode; 177 return (0); 178 } 179 180 int 181 freebsd11_procstat_get_socket_info(struct procstat *procstat, struct filestat *fst, 182 struct freebsd11_sockstat *sock_compat, char *errbuf) 183 { 184 struct sockstat sock; 185 int r; 186 187 r = procstat_get_socket_info(procstat, fst, &sock, errbuf); 188 if (r != 0) 189 return (r); 190 sock_compat->inp_ppcb = sock.inp_ppcb; 191 sock_compat->so_addr = sock.so_addr; 192 sock_compat->so_pcb = sock.so_pcb; 193 sock_compat->unp_conn = sock.unp_conn; 194 sock_compat->dom_family = sock.dom_family; 195 sock_compat->proto = sock.proto; 196 sock_compat->so_rcv_sb_state = sock.so_rcv_sb_state; 197 sock_compat->so_snd_sb_state = sock.so_snd_sb_state; 198 sock_compat->sa_local = sock.sa_local; 199 sock_compat->sa_peer = sock.sa_peer; 200 sock_compat->type = sock.type; 201 memcpy(sock_compat->dname, sock.dname, sizeof(sock.dname)); 202 return (0); 203 } 204 205 int 206 freebsd11_procstat_get_vnode_info(struct procstat *procstat, 207 struct filestat *fst, struct freebsd11_vnstat *vn_compat, char *errbuf) 208 { 209 struct vnstat vn; 210 int r; 211 212 r = procstat_get_vnode_info(procstat, fst, &vn, errbuf); 213 if (r != 0) 214 return (r); 215 vn_compat->vn_fileid = vn.vn_fileid; 216 vn_compat->vn_size = vn.vn_size; 217 vn_compat->vn_mntdir = vn.vn_mntdir; 218 vn_compat->vn_dev = vn.vn_dev; 219 vn_compat->vn_fsid = vn.vn_fsid; 220 vn_compat->vn_type = vn.vn_type; 221 vn_compat->vn_mode = vn.vn_mode; 222 if (strlen(vn.vn_devname) >= sizeof(vn_compat->vn_devname)) 223 strcpy(vn_compat->vn_devname, trunc_name); 224 else 225 memcpy(vn_compat->vn_devname, vn.vn_devname, 226 sizeof(vn_compat->vn_devname)); 227 return (0); 228 } 229 230 int 231 freebsd12_procstat_get_vnode_info(struct procstat *procstat, 232 struct filestat *fst, struct freebsd12_vnstat *vn_compat, char *errbuf) 233 { 234 struct vnstat vn; 235 int r; 236 237 r = procstat_get_vnode_info(procstat, fst, &vn, errbuf); 238 if (r != 0) 239 return (r); 240 vn_compat->vn_fileid = vn.vn_fileid; 241 vn_compat->vn_size = vn.vn_size; 242 vn_compat->vn_mntdir = vn.vn_mntdir; 243 vn_compat->vn_dev = vn.vn_dev; 244 vn_compat->vn_fsid = vn.vn_fsid; 245 vn_compat->vn_type = vn.vn_type; 246 vn_compat->vn_mode = vn.vn_mode; 247 if (strlen(vn.vn_devname) >= sizeof(vn_compat->vn_devname)) 248 strcpy(vn_compat->vn_devname, trunc_name); 249 else 250 memcpy(vn_compat->vn_devname, vn.vn_devname, 251 sizeof(vn_compat->vn_devname)); 252 return (0); 253 } 254 255 __sym_compat(procstat_get_pts_info, freebsd11_procstat_get_pts_info, FBSD_1.2); 256 __sym_compat(procstat_get_socket_info, freebsd11_procstat_get_socket_info, 257 FBSD_1.2); 258 __sym_compat(procstat_get_vnode_info, freebsd11_procstat_get_vnode_info, 259 FBSD_1.2); 260 __sym_compat(procstat_get_sem_info, freebsd11_procstat_get_sem_info, FBSD_1.3); 261 __sym_compat(procstat_get_shm_info, freebsd11_procstat_get_shm_info, FBSD_1.3); 262 __sym_compat(procstat_get_pts_info, freebsd12_procstat_get_pts_info, FBSD_1.5); 263 __sym_compat(procstat_get_vnode_info, freebsd12_procstat_get_vnode_info, 264 FBSD_1.5); 265