📄 parser.c
字号:
selection_list->typecode = SEL_PID; return NULL; /* can't have any more options */#ifdef KNOW_WHAT_TO_DO_WITH_THIS case 'r': trace("-r some Digital Unix thing about warnings...\n"); trace(" or SCO's option to chroot() for new /proc and /dev.\n"); return "The -r option is reserved."; break;#endif case 's': /* end */ trace("-s Select processes belonging to the sessions given.\n"); arg=get_opt_arg(); if(!arg) return "List of session IDs must follow -s."; err=parse_list(arg, parse_pid); if(err) return err; selection_list->typecode = SEL_SESS; return NULL; /* can't have any more options */ case 't': /* end */ trace("-t select by tty.\n"); arg=get_opt_arg(); if(!arg) return "List of terminals (pty, tty...) must follow -t."; err=parse_list(arg, parse_tty); if(err) return err; selection_list->typecode = SEL_TTY; return NULL; /* can't have any more options */ case 'u': /* end */ trace("-u select by user ID (the EUID?) (supports names).\n"); arg=get_opt_arg(); if(!arg) return "List of users must follow -p."; err=parse_list(arg, parse_uid); if(err) return err; selection_list->typecode = SEL_EUID; return NULL; /* can't have any more options */ case 'w': trace("-w wide output.\n"); w_count++; break;#ifdef NOBODY_HAS_BSD_HABITS_ANYMORE case 'x': /* Same as -y, but for System V Release 4 MP */ trace("-x works like Sun Solaris & SCO Unixware -y option\n"); format_modifiers |= FM_y; break;#endif case 'y': /* Sun's -l hack (also: Irix "lnode" resource control info) */ trace("-y Print lnone info in UID/USER column or do Sun -l hack.\n"); format_modifiers |= FM_y; break; case 'z': /* alias of Mandatory Access Control level info */ trace("-z shows aliased MAC info\n"); return "Don't understand MAC on Linux."; break; case '-': printf("ARRRGH!!! -\n"); return "Embedded '-' among SysV options makes no sense."; break; case '\0': printf("ARRRGH!!! \\0\n"); return "Please report the \"SysV \\0 can't happen\" bug."; break; default: return "Unsupported SysV option."; } /* switch */ } /* while */ return NULL;}/************************* parse BSD options **********************/static const char *parse_bsd_option(void){ const char *arg; const char *err;#if 0 fprintf(stderr, "(%s) %sforce_bsd %s(personality & PER_FORCE_BSD)\n", ps_argv[thisarg], (force_bsd?"":"!"), ((personality & PER_FORCE_BSD)?"":"!") );#endif flagptr = ps_argv[thisarg]; /* assume we _have_ a '-' */ if(flagptr[0]=='-'){ if(!force_bsd) return "Can't happen! Problem #1."; }else{ flagptr--; /* off beginning, will increment before use */ if(personality & PER_FORCE_BSD){ if(!force_bsd) return "Can't happen! Problem #2."; }else{ if(force_bsd) return "2nd chance parse failed, not BSD or SysV."; } } while(*++flagptr){ switch(*flagptr){ case 'A': /* maybe this just does a larger malloc() ? */ trace("A Increases the argument space (Digital Unix)\n"); return "Option A is reserved."; break; case 'C': /* should divide result by 1-(e**(foo*log(bar))) */ trace("C Use raw CPU time for %%CPU instead of decaying ave\n"); return "Option C is reserved."; break; case 'L': /* single */ trace("L List all format specifiers\n"); exclusive("L"); print_format_specifiers(); exit(0); case 'M': trace("M junk (use alternate core)\n"); return "Option M is unsupported, try N or -n instead."; break; case 'N': /* end */ trace("N Specify namelist file\n"); arg=get_opt_arg(); if(!arg) return "System.map or psdatabase must follow N."; namelist_file = arg; return NULL; /* can't have any more options */ case 'O': /* end */ trace("O Like o + defaults, add new columns after PID. Also sort.\n"); arg=get_opt_arg(); if(!arg) return "Format or sort specification must follow O."; defer_sf_option(arg, SF_B_O); return NULL; /* can't have any more options */ break; case 'S': trace("S include dead kids in sum\n"); include_dead_children = 1; break; case 'T': trace("T Select all processes on this terminal\n"); /* put our tty on a tiny list */ { selection_node *node; node = malloc(sizeof(selection_node)); node->u = malloc(sizeof(sel_union)); node->u[0].tty = cached_tty; node->typecode = SEL_TTY; node->n = 1; node->next = selection_list; selection_list = node; } break; case 'U': /* end */ trace("U Select processes for specified users.\n"); arg=get_opt_arg(); if(!arg) return "List of users must follow U."; err=parse_list(arg, parse_uid); if(err) return err; selection_list->typecode = SEL_EUID; return NULL; /* can't have any more options */ case 'V': /* single */ trace("V show version info\n"); exclusive("V"); display_version(); exit(0); case 'W': trace("W N/A get swap info from ... not /dev/drum.\n"); return "Obsolete W option not supported. (You have a /dev/drum?)"; break; case 'X': trace("X Old Linux i386 register format\n"); format_flags |= FF_LX; break; case 'a': trace("a Select all w/tty, including other users\n"); /* Now the PER_SUN_MUTATE_a flag is handled elsewhere. */ /* if(personality & PER_SUN_MUTATE_a) simple_select |= SS_U_a; else */ simple_select |= SS_B_a; break; case 'c': trace("c true command name\n"); bsd_c_option = 1; break; case 'e': trace("e environment\n"); bsd_e_option = 1; break; case 'f': trace("f ASCII art forest\n"); forest_type = 'b'; break; case 'g': trace("g _all_, even group leaders!.\n"); simple_select |= SS_B_g; break; case 'h': trace("h Repeat header... yow.\n"); if(header_type) return "Only one heading option may be specified."; if(personality & PER_BSD_h) header_type = HEAD_MULTI; else header_type = HEAD_NONE; break; case 'j': trace("j job control format\n"); format_flags |= FF_Bj; break; case 'k': trace("k N/A Use /vmcore as c-dumpfile\n"); return "Obsolete k option not supported."; break; case 'l': trace("l Display long format\n"); format_flags |= FF_Bl; break; case 'm': trace("m all threads, sort on mem use, show mem info\n"); if(personality & PER_OLD_m){ format_flags |= FF_Lm; break; } if(personality & PER_BSD_m){ defer_sf_option("pmem", SF_B_m); break; } return "Thread display not implemented."; break; case 'n': trace("n Numeric output for WCHAN and USER replaced by UID\n"); wchan_is_number = 1; user_is_number = 1; /* TODO add tty_is_number too? */ break; case 'o': /* end */ trace("o Specify user-defined format\n"); arg=get_opt_arg(); if(!arg) return "Format specification must follow -o."; defer_sf_option(arg, SF_B_o); return NULL; /* can't have any more options */ case 'p': /* end */ trace("p Select by process ID\n"); arg=get_opt_arg(); if(!arg) return "List of process IDs must follow p."; err=parse_list(arg, parse_pid); if(err) return err; selection_list->typecode = SEL_PID; return NULL; /* can't have any more options */ case 'r': trace("r Select running processes\n"); running_only = 1; break; case 's': trace("s Display signal format\n"); format_flags |= FF_Bs; break; case 't': /* end */ trace("t Select by tty.\n"); /* List of terminals (tty, pty...) _should_ follow t. */ arg=get_opt_arg(); if(!arg){ /* Wow, obsolete BSD syntax. Put our tty on a tiny list. */ selection_node *node; node = malloc(sizeof(selection_node)); node->u = malloc(sizeof(sel_union)); node->u[0].tty = cached_tty; node->typecode = SEL_TTY; node->n = 1; node->next = selection_list; selection_list = node; return NULL; } err=parse_list(arg, parse_tty); if(err) return err; selection_list->typecode = SEL_TTY; return NULL; /* can't have any more options */ case 'u': trace("u Display user-oriented\n"); format_flags |= FF_Bu; break; case 'v': trace("v Display virtual memory\n"); format_flags |= FF_Bv; break; case 'w': trace("w wide output\n"); w_count++; break; case 'x': trace("x Select processes without controlling ttys\n"); simple_select |= SS_B_x; break; case '-': printf("ARRRGH!!! -\n"); return "Embedded '-' among BSD options makes no sense."; break; case '\0': printf("ARRRGH!!! \\0\n"); return "Please report the \"BSD \\0 can't happen\" bug."; break; default: if (*flagptr >= '0' && *flagptr <= '9') { /* BSD syntax allows (in fact, on some systems requires) * being able to include the pid after the options with * NO intervening space. :-( */ selection_node *pidnode; pidnode = calloc(1, sizeof(selection_node)); pidnode->u = calloc(1, sizeof(sel_union)); pidnode->n = 1; parse_pid(flagptr, pidnode->u); pidnode->next = selection_list; selection_list = pidnode; selection_list->typecode = SEL_PID; return NULL; /* do not iterate over the rest of the digits */ } else { return "Unsupported option (BSD syntax)"; } } /* switch */ } /* while */ return NULL;}/*************** gnu long options **********************//* * Return the argument or NULL */static const char *grab_gnu_arg(void){ switch(*flagptr){ /* argument is part of ps_argv[thisarg] */ default: return NULL; /* something bad */ case '=': case ':': if(*++flagptr) return flagptr; /* found it */ return NULL; /* empty '=' or ':' */ case '\0': /* try next argv[] */ } if(thisarg+2 > ps_argc) return NULL; /* there is nothing left */ /* argument follows ps_argv[thisarg] */ if(*(ps_argv[thisarg+1]) == '\0') return NULL; return ps_argv[++thisarg];}typedef struct gnu_table_struct { const char *name; /* long option name */ const void *jump; /* See gcc extension info. :-) */} gnu_table_struct;static int compare_gnu_table_structs(const void *a, const void *b){ return strcmp(((gnu_table_struct*)a)->name,((gnu_table_struct*)b)->name);}/* Option arguments are after ':', after '=', or in argv[n+1] */static const char *parse_gnu_option(void){ const char *arg; const char *err; char *s; size_t sl; char buf[16]; gnu_table_struct findme = { buf, NULL}; gnu_table_struct *found; static const gnu_table_struct gnu_table[] = { {"Group", &&case_Group}, /* rgid */ {"User", &&case_User}, /* ruid */ {"cols", &&case_cols}, {"columns", &&case_columns}, {"cumulative", &&case_cumulative}, {"deselect", &&case_deselect}, /* -N */ {"forest", &&case_forest}, /* f -H */ {"format", &&case_format}, {"group", &&case_group}, /* egid */ {"header", &&case_header}, {"headers", &&case_headers}, {"heading", &&case_heading}, {"headings", &&case_headings}, {"help", &&case_help}, {"html", &&case_html}, {"info", &&case_info}, {"lines", &&case_lines}, {"no-header", &&case_no_header}, {"no-headers", &&case_no_headers}, {"no-heading", &&case_no_heading}, {"no-headings", &&case_no_headings}, {"noheader", &&case_noheader}, {"noheaders", &&case_noheaders}, {"noheading", &&case_noheading}, {"noheadings", &&case_noheadings}, {"nul", &&case_nul}, {"null", &&case_null}, {"pid", &&case_pid}, {"rows", &&case_rows}, {"sid", &&case_sid}, {"sort", &&case_sort}, {"tty", &&case_tty},
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -