structtask_struct { #ifdef CONFIG_THREAD_INFO_IN_TASK /* * For reasons of header soup (see current_thread_info()), this * must be the first element of task_struct. */ structthread_infothread_info; #endif unsignedint __state;
#ifdef CONFIG_PREEMPT_RT /* saved state for "spinlock sleepers" */ unsignedint saved_state; #endif ......此处省略114514行。 };
structPSTREE { pid_t pid; // Child process. structPSTREE *child; // The next node, it has the same parent process with current node. structPSTREE *next; };
struct PSTREE *add_pid(struct PSTREE *pstree, pid_t pid) { /* * If current pstree struct is NULL, add pid info here. * Or we try the ->next node. */ if (pstree == NULL) { pstree = (struct PSTREE *)malloc(sizeof(struct PSTREE)); pstree->pid = pid; pstree->next = NULL; pstree->child = NULL; return pstree; } pstree->next = add_pid(pstree->next, pid); return pstree; } struct PSTREE *add_child(struct PSTREE *pstree, pid_t ppid, pid_t pid) { /* * If we find ppid in pstree nodes, add pid to the child struct of its ppid. * Or this function will do nothing. * So we can always run add_child(pstree,ppid,pid) to check && add a pid. */ if (pstree == NULL) { returnNULL; } if (pstree->pid == ppid) { pstree->child = add_pid(pstree->child, pid); return pstree; } pstree->next = add_child(pstree->next, ppid, pid); pstree->child = add_child(pstree->child, ppid, pid); return pstree; }
voidprint_tree(struct PSTREE *pstree, int depth) { /* * How this function works: * Print info of current pid. * Print info of the child tree of current pid. * Print info of ->next node. × So that it will walk all the nodes. */ if (pstree == NULL) { return; } char *color[] = {"\033[1;38;2;0;0;255m", "\033[1;38;2;0;255;0m", "\033[1;38;2;255;0;0m"}; if (depth > 0) { for (int i = 0; i < depth + 1; i++) { printf("%s: ", color[i % 3]); } printf("\n"); for (int i = 0; i < depth; i++) { printf("%s: ", color[i % 3]); } printf("%s:·> ", color[depth % 3]); } char *stat = getpid_stat(pstree->pid); char *name = getpid_name(pstree->pid); printf("\033[1;38;2;137;180;250m%d\033[1;38;2;245;194;231m (%s) \033[1;38;2;254;228;208m%s\n", pstree->pid, stat, name); free(name); free(stat); print_tree(pstree->child, depth + 1); print_tree(pstree->next, depth); }
voidpstree(pid_t parent) { /* * This function gets the pid that is bigger than parent, * Try to add them to pstree struct if they are child of parent that is given. * then call print_tree to print pid tree info. */ DIR *proc_dir = opendir("/proc"); structdirent *file =NULL; int len = 0; while ((file = readdir(proc_dir)) != NULL) { if (file->d_type == DT_DIR) { if (atoi(file->d_name) > parent) { len++; } } } seekdir(proc_dir, 0); int pids[len + 1]; // For passing clang-tidy. memset(pids, 0, sizeof(pids)); int i = 0; while ((file = readdir(proc_dir)) != NULL) { if (file->d_type == DT_DIR) { if (atoi(file->d_name) > parent) { pids[i] = atoi(file->d_name); i++; } } } closedir(proc_dir); structPSTREE *pstree =NULL; pstree = add_pid(pstree, parent); for (int j = 0; j < len; j++) { pstree = add_child(pstree, get_ppid(pids[j]), pids[j]); } print_tree(pstree, 0); free(pstree); }