print.c revision 189078
11558Srgrimes/*- 21558Srgrimes * Copyright (c) 1990, 1993, 1994 31558Srgrimes * The Regents of the University of California. All rights reserved. 41558Srgrimes * 51558Srgrimes * Redistribution and use in source and binary forms, with or without 61558Srgrimes * modification, are permitted provided that the following conditions 71558Srgrimes * are met: 81558Srgrimes * 1. Redistributions of source code must retain the above copyright 91558Srgrimes * notice, this list of conditions and the following disclaimer. 101558Srgrimes * 2. Redistributions in binary form must reproduce the above copyright 111558Srgrimes * notice, this list of conditions and the following disclaimer in the 121558Srgrimes * documentation and/or other materials provided with the distribution. 131558Srgrimes * 4. Neither the name of the University nor the names of its contributors 141558Srgrimes * may be used to endorse or promote products derived from this software 151558Srgrimes * without specific prior written permission. 161558Srgrimes * 171558Srgrimes * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 181558Srgrimes * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 191558Srgrimes * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 201558Srgrimes * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 211558Srgrimes * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 221558Srgrimes * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 231558Srgrimes * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 241558Srgrimes * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 251558Srgrimes * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 261558Srgrimes * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 271558Srgrimes * SUCH DAMAGE. 281558Srgrimes */ 291558Srgrimes 301558Srgrimes#if 0 311558Srgrimes#ifndef lint 321558Srgrimesstatic char sccsid[] = "@(#)print.c 8.6 (Berkeley) 4/16/94"; 331558Srgrimes#endif /* not lint */ 3417347Sbde#endif 351558Srgrimes 361558Srgrimes#include <sys/cdefs.h> 371558Srgrimes__FBSDID("$FreeBSD: head/bin/ps/print.c 189078 2009-02-26 18:01:07Z attilio $"); 381558Srgrimes 391558Srgrimes#include <sys/param.h> 4017347Sbde#include <sys/time.h> 411558Srgrimes#include <sys/resource.h> 4237422Scharnier#include <sys/proc.h> 4317347Sbde#include <sys/stat.h> 4450476Speter 451558Srgrimes#include <sys/mac.h> 461558Srgrimes#include <sys/user.h> 471558Srgrimes#include <sys/sysctl.h> 481558Srgrimes 4917347Sbde#include <err.h> 5037422Scharnier#include <grp.h> 5117347Sbde#include <langinfo.h> 521558Srgrimes#include <locale.h> 5317347Sbde#include <math.h> 5417347Sbde#include <nlist.h> 5555496Sobrien#include <pwd.h> 5655496Sobrien#include <stddef.h> 5755496Sobrien#include <stdio.h> 581558Srgrimes#include <stdlib.h> 5937422Scharnier#include <string.h> 60170653Sdelphij#include <unistd.h> 6137422Scharnier#include <vis.h> 6255496Sobrien 6355496Sobrien#include "ps.h" 64203277Sed 65203277Sed#define ps_pgtok(a) (((a) * getpagesize()) / 1024) 6637422Scharnier 6737422Scharniervoid 6837422Scharnierprintheader(void) 6955496Sobrien{ 70170653Sdelphij VAR *v; 7155496Sobrien struct varent *vent; 7255496Sobrien 7355496Sobrien STAILQ_FOREACH(vent, &varlist, next_ve) 7455496Sobrien if (*vent->header != '\0') 7555496Sobrien break; 7655496Sobrien if (!vent) 7755496Sobrien return; 7855496Sobrien 7955496Sobrien STAILQ_FOREACH(vent, &varlist, next_ve) { 8055496Sobrien v = vent->var; 8155496Sobrien if (v->flag & LJUST) { 8255496Sobrien if (STAILQ_NEXT(vent, next_ve) == NULL) /* last one */ 8355496Sobrien (void)printf("%s", vent->header); 8455496Sobrien else 8555496Sobrien (void)printf("%-*s", v->width, vent->header); 8655496Sobrien } else 8755496Sobrien (void)printf("%*s", v->width, vent->header); 8855496Sobrien if (STAILQ_NEXT(vent, next_ve) != NULL) 89170653Sdelphij (void)putchar(' '); 9055496Sobrien } 9155496Sobrien (void)putchar('\n'); 9255496Sobrien} 9355496Sobrien 9455496Sobrienvoid 9555496Sobrienarguments(KINFO *k, VARENT *ve) 9655496Sobrien{ 9755496Sobrien VAR *v; 9855496Sobrien int left; 99170653Sdelphij char *cp, *vis_args; 10055496Sobrien 10155496Sobrien v = ve->var; 10255496Sobrien if ((vis_args = malloc(strlen(k->ki_args) * 4 + 1)) == NULL) 10355496Sobrien errx(1, "malloc failed"); 10455496Sobrien strvis(vis_args, k->ki_args, VIS_TAB | VIS_NL | VIS_NOSLASH); 10555496Sobrien if (STAILQ_NEXT(ve, next_ve) == NULL) { 10655496Sobrien /* last field */ 10755496Sobrien if (termwidth == UNLIMITED) { 10817347Sbde (void)printf("%s", vis_args); 109170653Sdelphij } else { 1101558Srgrimes left = termwidth - (totwidth - v->width); 11155496Sobrien if (left < 1) /* already wrapped, just use std width */ 11255496Sobrien left = v->width; 11355496Sobrien for (cp = vis_args; --left >= 0 && *cp != '\0';) 11455496Sobrien (void)putchar(*cp++); 11517347Sbde } 11655496Sobrien } else { 11746859Sphk (void)printf("%-*.*s", v->width, v->width, vis_args); 1181558Srgrimes } 119203277Sed free(vis_args); 12037422Scharnier} 1211558Srgrimes 122203277Sedvoid 123203277Sedcommand(KINFO *k, VARENT *ve) 124203277Sed{ 125203277Sed VAR *v; 126203277Sed int left; 127203277Sed char *cp, *vis_env, *vis_args; 128203277Sed 129203277Sed v = ve->var; 1301558Srgrimes if (cflag) { 131203277Sed /* If it is the last field, then don't pad */ 132203277Sed if (STAILQ_NEXT(ve, next_ve) == NULL) { 133203277Sed (void)printf("%s", k->ki_p->ki_comm); 134203277Sed if (showthreads && k->ki_p->ki_numthreads > 1) 135203277Sed printf("/%s", k->ki_p->ki_ocomm); 136203277Sed } else 137203277Sed (void)printf("%-*s", v->width, k->ki_p->ki_comm); 138203277Sed return; 139203277Sed } 140203277Sed if ((vis_args = malloc(strlen(k->ki_args) * 4 + 1)) == NULL) 141203277Sed errx(1, "malloc failed"); 142215704Sbrucec strvis(vis_args, k->ki_args, VIS_TAB | VIS_NL | VIS_NOSLASH); 143203277Sed if (k->ki_env) { 144203277Sed if ((vis_env = malloc(strlen(k->ki_env) * 4 + 1)) == NULL) 145203277Sed errx(1, "malloc failed"); 146203277Sed strvis(vis_env, k->ki_env, VIS_TAB | VIS_NL | VIS_NOSLASH); 147203277Sed } else 148203277Sed vis_env = NULL; 14917302Sjoerg 15055496Sobrien if (STAILQ_NEXT(ve, next_ve) == NULL) { 15155496Sobrien /* last field */ 15255496Sobrien if (termwidth == UNLIMITED) { 15355496Sobrien if (vis_env) 15455496Sobrien (void)printf("%s ", vis_env); 15555496Sobrien (void)printf("%s", vis_args); 15655496Sobrien } else { 15755496Sobrien left = termwidth - (totwidth - v->width); 15855496Sobrien if (left < 1) /* already wrapped, just use std width */ 15955496Sobrien left = v->width; 16055496Sobrien if ((cp = vis_env) != NULL) { 16126674Scharnier while (--left >= 0 && *cp) 16226674Scharnier (void)putchar(*cp++); 16355496Sobrien if (--left >= 0) 16455496Sobrien putchar(' '); 16555496Sobrien } 1661558Srgrimes for (cp = vis_args; --left >= 0 && *cp != '\0';) 1671558Srgrimes (void)putchar(*cp++); 168 } 169 } else 170 /* XXX env? */ 171 (void)printf("%-*.*s", v->width, v->width, vis_args); 172 free(vis_args); 173 if (vis_env != NULL) 174 free(vis_env); 175} 176 177void 178ucomm(KINFO *k, VARENT *ve) 179{ 180 char tmpbuff[COMMLEN + OCOMMLEN + 2]; 181 VAR *v; 182 183 v = ve->var; 184 if (STAILQ_NEXT(ve, next_ve) == NULL) { /* last field, don't pad */ 185 (void)printf("%s", k->ki_p->ki_comm); 186 if (showthreads && k->ki_p->ki_numthreads > 1) 187 printf("/%s", k->ki_p->ki_ocomm); 188 } else { 189 bzero(tmpbuff, sizeof(tmpbuff)); 190 if (showthreads && k->ki_p->ki_numthreads > 1) 191 sprintf(tmpbuff, "%s/%s", k->ki_p->ki_comm, 192 k->ki_p->ki_ocomm); 193 else 194 sprintf(tmpbuff, "%s", k->ki_p->ki_comm); 195 (void)printf("%-*s", v->width, tmpbuff); 196 } 197} 198 199void 200tdnam(KINFO *k, VARENT *ve) 201{ 202 VAR *v; 203 204 v = ve->var; 205 if (showthreads && k->ki_p->ki_numthreads > 1) 206 (void)printf("%-*s", v->width, k->ki_p->ki_ocomm); 207 else 208 (void)printf("%-*s", v->width, " "); 209} 210 211void 212logname(KINFO *k, VARENT *ve) 213{ 214 VAR *v; 215 char *s; 216 217 v = ve->var; 218 (void)printf("%-*s", v->width, (s = k->ki_p->ki_login, *s) ? s : "-"); 219} 220 221void 222state(KINFO *k, VARENT *ve) 223{ 224 int flag, tdflags; 225 char *cp; 226 VAR *v; 227 char buf[16]; 228 229 v = ve->var; 230 flag = k->ki_p->ki_flag; 231 tdflags = k->ki_p->ki_tdflags; /* XXXKSE */ 232 cp = buf; 233 234 switch (k->ki_p->ki_stat) { 235 236 case SSTOP: 237 *cp = 'T'; 238 break; 239 240 case SSLEEP: 241 if (tdflags & TDF_SINTR) /* interruptable (long) */ 242 *cp = k->ki_p->ki_slptime >= MAXSLP ? 'I' : 'S'; 243 else 244 *cp = 'D'; 245 break; 246 247 case SRUN: 248 case SIDL: 249 *cp = 'R'; 250 break; 251 252 case SWAIT: 253 *cp = 'W'; 254 break; 255 256 case SLOCK: 257 *cp = 'L'; 258 break; 259 260 case SZOMB: 261 *cp = 'Z'; 262 break; 263 264 default: 265 *cp = '?'; 266 } 267 cp++; 268 if (!(flag & P_INMEM)) 269 *cp++ = 'W'; 270 if (k->ki_p->ki_nice < NZERO) 271 *cp++ = '<'; 272 else if (k->ki_p->ki_nice > NZERO) 273 *cp++ = 'N'; 274 if (flag & P_TRACED) 275 *cp++ = 'X'; 276 if (flag & P_WEXIT && k->ki_p->ki_stat != SZOMB) 277 *cp++ = 'E'; 278 if (flag & P_PPWAIT) 279 *cp++ = 'V'; 280 if ((flag & P_SYSTEM) || k->ki_p->ki_lock > 0) 281 *cp++ = 'L'; 282 if (k->ki_p->ki_kiflag & KI_SLEADER) 283 *cp++ = 's'; 284 if ((flag & P_CONTROLT) && k->ki_p->ki_pgid == k->ki_p->ki_tpgid) 285 *cp++ = '+'; 286 if (flag & P_JAILED) 287 *cp++ = 'J'; 288 *cp = '\0'; 289 (void)printf("%-*s", v->width, buf); 290} 291 292#define scalepri(x) ((x) - PZERO) 293 294void 295pri(KINFO *k, VARENT *ve) 296{ 297 VAR *v; 298 299 v = ve->var; 300 (void)printf("%*d", v->width, scalepri(k->ki_p->ki_pri.pri_level)); 301} 302 303void 304upr(KINFO *k, VARENT *ve) 305{ 306 VAR *v; 307 308 v = ve->var; 309 (void)printf("%*d", v->width, scalepri(k->ki_p->ki_pri.pri_user)); 310} 311#undef scalepri 312 313void 314uname(KINFO *k, VARENT *ve) 315{ 316 VAR *v; 317 318 v = ve->var; 319 (void)printf("%-*s", v->width, user_from_uid(k->ki_p->ki_uid, 0)); 320} 321 322int 323s_uname(KINFO *k) 324{ 325 return (strlen(user_from_uid(k->ki_p->ki_uid, 0))); 326} 327 328void 329rgroupname(KINFO *k, VARENT *ve) 330{ 331 VAR *v; 332 333 v = ve->var; 334 (void)printf("%-*s", v->width, group_from_gid(k->ki_p->ki_rgid, 0)); 335} 336 337int 338s_rgroupname(KINFO *k) 339{ 340 return (strlen(group_from_gid(k->ki_p->ki_rgid, 0))); 341} 342 343void 344runame(KINFO *k, VARENT *ve) 345{ 346 VAR *v; 347 348 v = ve->var; 349 (void)printf("%-*s", v->width, user_from_uid(k->ki_p->ki_ruid, 0)); 350} 351 352int 353s_runame(KINFO *k) 354{ 355 return (strlen(user_from_uid(k->ki_p->ki_ruid, 0))); 356} 357 358 359void 360tdev(KINFO *k, VARENT *ve) 361{ 362 VAR *v; 363 dev_t dev; 364 char buff[16]; 365 366 v = ve->var; 367 dev = k->ki_p->ki_tdev; 368 if (dev == NODEV) 369 (void)printf("%*s", v->width, "??"); 370 else { 371 (void)snprintf(buff, sizeof(buff), 372 "%d/%d", major(dev), minor(dev)); 373 (void)printf("%*s", v->width, buff); 374 } 375} 376 377void 378tname(KINFO *k, VARENT *ve) 379{ 380 VAR *v; 381 dev_t dev; 382 char *ttname; 383 384 v = ve->var; 385 dev = k->ki_p->ki_tdev; 386 if (dev == NODEV || (ttname = devname(dev, S_IFCHR)) == NULL) 387 (void)printf("%*s ", v->width - 1, "??"); 388 else { 389 if (strncmp(ttname, "tty", 3) == 0 || 390 strncmp(ttname, "cua", 3) == 0) 391 ttname += 3; 392 if (strncmp(ttname, "pts/", 4) == 0) 393 ttname += 4; 394 (void)printf("%*.*s%c", v->width - 1, v->width - 1, ttname, 395 k->ki_p->ki_kiflag & KI_CTTY ? ' ' : '-'); 396 } 397} 398 399void 400longtname(KINFO *k, VARENT *ve) 401{ 402 VAR *v; 403 dev_t dev; 404 char *ttname; 405 406 v = ve->var; 407 dev = k->ki_p->ki_tdev; 408 if (dev == NODEV || (ttname = devname(dev, S_IFCHR)) == NULL) 409 (void)printf("%-*s", v->width, "??"); 410 else 411 (void)printf("%-*s", v->width, ttname); 412} 413 414void 415started(KINFO *k, VARENT *ve) 416{ 417 VAR *v; 418 time_t then; 419 struct tm *tp; 420 static int use_ampm = -1; 421 char buf[100]; 422 423 v = ve->var; 424 if (!k->ki_valid) { 425 (void)printf("%-*s", v->width, "-"); 426 return; 427 } 428 if (use_ampm < 0) 429 use_ampm = (*nl_langinfo(T_FMT_AMPM) != '\0'); 430 then = k->ki_p->ki_start.tv_sec; 431 tp = localtime(&then); 432 if (now - k->ki_p->ki_start.tv_sec < 24 * 3600) { 433 (void)strftime(buf, sizeof(buf), 434 use_ampm ? "%l:%M%p" : "%k:%M ", tp); 435 } else if (now - k->ki_p->ki_start.tv_sec < 7 * 86400) { 436 (void)strftime(buf, sizeof(buf), 437 use_ampm ? "%a%I%p" : "%a%H ", tp); 438 } else 439 (void)strftime(buf, sizeof(buf), "%e%b%y", tp); 440 (void)printf("%-*s", v->width, buf); 441} 442 443void 444lstarted(KINFO *k, VARENT *ve) 445{ 446 VAR *v; 447 time_t then; 448 char buf[100]; 449 450 v = ve->var; 451 if (!k->ki_valid) { 452 (void)printf("%-*s", v->width, "-"); 453 return; 454 } 455 then = k->ki_p->ki_start.tv_sec; 456 (void)strftime(buf, sizeof(buf), "%c", localtime(&then)); 457 (void)printf("%-*s", v->width, buf); 458} 459 460void 461lockname(KINFO *k, VARENT *ve) 462{ 463 VAR *v; 464 465 v = ve->var; 466 if (k->ki_p->ki_kiflag & KI_LOCKBLOCK) { 467 if (k->ki_p->ki_lockname[0] != 0) 468 (void)printf("%-*.*s", v->width, v->width, 469 k->ki_p->ki_lockname); 470 else 471 (void)printf("%-*s", v->width, "???"); 472 } else 473 (void)printf("%-*s", v->width, "-"); 474} 475 476void 477wchan(KINFO *k, VARENT *ve) 478{ 479 VAR *v; 480 481 v = ve->var; 482 if (k->ki_p->ki_wchan) { 483 if (k->ki_p->ki_wmesg[0] != 0) 484 (void)printf("%-*.*s", v->width, v->width, 485 k->ki_p->ki_wmesg); 486 else 487 (void)printf("%-*lx", v->width, 488 (long)k->ki_p->ki_wchan); 489 } else 490 (void)printf("%-*s", v->width, "-"); 491} 492 493void 494nwchan(KINFO *k, VARENT *ve) 495{ 496 VAR *v; 497 498 v = ve->var; 499 if (k->ki_p->ki_wchan) { 500 (void)printf("%0*lx", v->width, 501 (long)k->ki_p->ki_wchan); 502 } else 503 (void)printf("%-*s", v->width, "-"); 504} 505 506void 507mwchan(KINFO *k, VARENT *ve) 508{ 509 VAR *v; 510 511 v = ve->var; 512 if (k->ki_p->ki_wchan) { 513 if (k->ki_p->ki_wmesg[0] != 0) 514 (void)printf("%-*.*s", v->width, v->width, 515 k->ki_p->ki_wmesg); 516 else 517 (void)printf("%-*lx", v->width, 518 (long)k->ki_p->ki_wchan); 519 } else if (k->ki_p->ki_kiflag & KI_LOCKBLOCK) { 520 if (k->ki_p->ki_lockname[0]) { 521 (void)printf("%-*.*s", v->width, v->width, 522 k->ki_p->ki_lockname); 523 } else 524 (void)printf("%-*s", v->width, "???"); 525 } else 526 (void)printf("%-*s", v->width, "-"); 527} 528 529void 530vsize(KINFO *k, VARENT *ve) 531{ 532 VAR *v; 533 534 v = ve->var; 535 (void)printf("%*lu", v->width, (u_long)(k->ki_p->ki_size / 1024)); 536} 537 538void 539cputime(KINFO *k, VARENT *ve) 540{ 541 VAR *v; 542 long secs; 543 long psecs; /* "parts" of a second. first micro, then centi */ 544 char obuff[128]; 545 static char decimal_point; 546 547 if (decimal_point == '\0') 548 decimal_point = localeconv()->decimal_point[0]; 549 v = ve->var; 550 if (!k->ki_valid) { 551 secs = 0; 552 psecs = 0; 553 } else { 554 /* 555 * This counts time spent handling interrupts. We could 556 * fix this, but it is not 100% trivial (and interrupt 557 * time fractions only work on the sparc anyway). XXX 558 */ 559 secs = k->ki_p->ki_runtime / 1000000; 560 psecs = k->ki_p->ki_runtime % 1000000; 561 if (sumrusage) { 562 secs += k->ki_p->ki_childtime.tv_sec; 563 psecs += k->ki_p->ki_childtime.tv_usec; 564 } 565 /* 566 * round and scale to 100's 567 */ 568 psecs = (psecs + 5000) / 10000; 569 secs += psecs / 100; 570 psecs = psecs % 100; 571 } 572 (void)snprintf(obuff, sizeof(obuff), "%3ld:%02ld%c%02ld", 573 secs / 60, secs % 60, decimal_point, psecs); 574 (void)printf("%*s", v->width, obuff); 575} 576 577void 578elapsed(KINFO *k, VARENT *ve) 579{ 580 VAR *v; 581 time_t val; 582 int days, hours, mins, secs; 583 char obuff[128]; 584 585 v = ve->var; 586 val = now - k->ki_p->ki_start.tv_sec; 587 days = val / (24 * 60 * 60); 588 val %= 24 * 60 * 60; 589 hours = val / (60 * 60); 590 val %= 60 * 60; 591 mins = val / 60; 592 secs = val % 60; 593 if (days != 0) 594 (void)snprintf(obuff, sizeof(obuff), "%3d-%02d:%02d:%02d", 595 days, hours, mins, secs); 596 else if (hours != 0) 597 (void)snprintf(obuff, sizeof(obuff), "%02d:%02d:%02d", 598 hours, mins, secs); 599 else 600 (void)snprintf(obuff, sizeof(obuff), "%02d:%02d", mins, secs); 601 (void)printf("%*s", v->width, obuff); 602} 603 604double 605getpcpu(const KINFO *k) 606{ 607 static int failure; 608 609 if (!nlistread) 610 failure = donlist(); 611 if (failure) 612 return (0.0); 613 614#define fxtofl(fixpt) ((double)(fixpt) / fscale) 615 616 /* XXX - I don't like this */ 617 if (k->ki_p->ki_swtime == 0 || (k->ki_p->ki_flag & P_INMEM) == 0) 618 return (0.0); 619 if (rawcpu) 620 return (100.0 * fxtofl(k->ki_p->ki_pctcpu)); 621 return (100.0 * fxtofl(k->ki_p->ki_pctcpu) / 622 (1.0 - exp(k->ki_p->ki_swtime * log(fxtofl(ccpu))))); 623} 624 625void 626pcpu(KINFO *k, VARENT *ve) 627{ 628 VAR *v; 629 630 v = ve->var; 631 (void)printf("%*.1f", v->width, getpcpu(k)); 632} 633 634static double 635getpmem(KINFO *k) 636{ 637 static int failure; 638 double fracmem; 639 640 if (!nlistread) 641 failure = donlist(); 642 if (failure) 643 return (0.0); 644 645 if ((k->ki_p->ki_flag & P_INMEM) == 0) 646 return (0.0); 647 /* XXX want pmap ptpages, segtab, etc. (per architecture) */ 648 /* XXX don't have info about shared */ 649 fracmem = ((float)k->ki_p->ki_rssize) / mempages; 650 return (100.0 * fracmem); 651} 652 653void 654pmem(KINFO *k, VARENT *ve) 655{ 656 VAR *v; 657 658 v = ve->var; 659 (void)printf("%*.1f", v->width, getpmem(k)); 660} 661 662void 663pagein(KINFO *k, VARENT *ve) 664{ 665 VAR *v; 666 667 v = ve->var; 668 (void)printf("%*ld", v->width, 669 k->ki_valid ? k->ki_p->ki_rusage.ru_majflt : 0); 670} 671 672/* ARGSUSED */ 673void 674maxrss(KINFO *k __unused, VARENT *ve) 675{ 676 VAR *v; 677 678 v = ve->var; 679 /* XXX not yet */ 680 (void)printf("%*s", v->width, "-"); 681} 682 683void 684priorityr(KINFO *k, VARENT *ve) 685{ 686 VAR *v; 687 struct priority *lpri; 688 char str[8]; 689 unsigned class, level; 690 691 v = ve->var; 692 lpri = &k->ki_p->ki_pri; 693 class = lpri->pri_class; 694 level = lpri->pri_level; 695 switch (class) { 696 case PRI_ITHD: 697 snprintf(str, sizeof(str), "intr:%u", level); 698 break; 699 case PRI_REALTIME: 700 snprintf(str, sizeof(str), "real:%u", level); 701 break; 702 case PRI_TIMESHARE: 703 strncpy(str, "normal", sizeof(str)); 704 break; 705 case PRI_IDLE: 706 snprintf(str, sizeof(str), "idle:%u", level); 707 break; 708 default: 709 snprintf(str, sizeof(str), "%u:%u", class, level); 710 break; 711 } 712 str[sizeof(str) - 1] = '\0'; 713 (void)printf("%*s", v->width, str); 714} 715 716/* 717 * Generic output routines. Print fields from various prototype 718 * structures. 719 */ 720static void 721printval(void *bp, VAR *v) 722{ 723 static char ofmt[32] = "%"; 724 const char *fcp; 725 char *cp; 726 727 cp = ofmt + 1; 728 fcp = v->fmt; 729 if (v->flag & LJUST) 730 *cp++ = '-'; 731 *cp++ = '*'; 732 while ((*cp++ = *fcp++)); 733 734#define CHKINF127(n) (((n) > 127) && (v->flag & INF127) ? 127 : (n)) 735 736 switch (v->type) { 737 case CHAR: 738 (void)printf(ofmt, v->width, *(char *)bp); 739 break; 740 case UCHAR: 741 (void)printf(ofmt, v->width, *(u_char *)bp); 742 break; 743 case SHORT: 744 (void)printf(ofmt, v->width, *(short *)bp); 745 break; 746 case USHORT: 747 (void)printf(ofmt, v->width, *(u_short *)bp); 748 break; 749 case INT: 750 (void)printf(ofmt, v->width, *(int *)bp); 751 break; 752 case UINT: 753 (void)printf(ofmt, v->width, CHKINF127(*(u_int *)bp)); 754 break; 755 case LONG: 756 (void)printf(ofmt, v->width, *(long *)bp); 757 break; 758 case ULONG: 759 (void)printf(ofmt, v->width, *(u_long *)bp); 760 break; 761 case KPTR: 762 (void)printf(ofmt, v->width, *(u_long *)bp); 763 break; 764 case PGTOK: 765 (void)printf(ofmt, v->width, ps_pgtok(*(u_long *)bp)); 766 break; 767 default: 768 errx(1, "unknown type %d", v->type); 769 } 770} 771 772void 773kvar(KINFO *k, VARENT *ve) 774{ 775 VAR *v; 776 777 v = ve->var; 778 printval((char *)((char *)k->ki_p + v->off), v); 779} 780 781void 782rvar(KINFO *k, VARENT *ve) 783{ 784 VAR *v; 785 786 v = ve->var; 787 if (k->ki_valid) 788 printval((char *)((char *)(&k->ki_p->ki_rusage) + v->off), v); 789 else 790 (void)printf("%*s", v->width, "-"); 791} 792 793void 794emulname(KINFO *k, VARENT *ve) 795{ 796 VAR *v; 797 798 v = ve->var; 799 printf("%-*s", v->width, *k->ki_p->ki_emul ? k->ki_p->ki_emul : "-"); 800} 801 802void 803label(KINFO *k, VARENT *ve) 804{ 805 char *string; 806 VAR *v; 807 mac_t proclabel; 808 int error; 809 810 v = ve->var; 811 string = NULL; 812 if (mac_prepare_process_label(&proclabel) == -1) { 813 warn("mac_prepare_process_label"); 814 goto out; 815 } 816 error = mac_get_pid(k->ki_p->ki_pid, proclabel); 817 if (error == 0) { 818 if (mac_to_text(proclabel, &string) == -1) 819 string = NULL; 820 } 821 mac_free(proclabel); 822out: 823 if (string != NULL) { 824 (void)printf("%-*s", v->width, string); 825 free(string); 826 } else 827 (void)printf("%-*s", v->width, " -"); 828 return; 829} 830 831int 832s_comm(KINFO *k) 833{ 834 char tmpbuff[COMMLEN + OCOMMLEN + 2]; 835 836 bzero(tmpbuff, sizeof(tmpbuff)); 837 if (showthreads && k->ki_p->ki_numthreads > 1) 838 sprintf(tmpbuff, "%s/%s", k->ki_p->ki_comm, 839 k->ki_p->ki_ocomm); 840 else 841 sprintf(tmpbuff, "%s", k->ki_p->ki_comm); 842 return (strlen(tmpbuff)); 843} 844 845int 846s_label(KINFO *k) 847{ 848 char *string = NULL; 849 mac_t proclabel; 850 int error, size = 0; 851 852 if (mac_prepare_process_label(&proclabel) == -1) { 853 warn("mac_prepare_process_label"); 854 return (0); 855 } 856 error = mac_get_pid(k->ki_p->ki_pid, proclabel); 857 if (error == 0 && mac_to_text(proclabel, &string) == 0) { 858 size = strlen(string); 859 free(string); 860 } 861 mac_free(proclabel); 862 return (size); 863} 864