tis.sandor
tis.sandor

Reputation: 171

How to list all users and the number of processes they have active

I've got a task to write a program that lists all active users, and the ammount of processes they have active, when the program receives a SIGHUP signal, and exits, when it gets a SIGINT signal.

I've got this for listing users and process count

ps -u "$(echo $(w -h | cut -d ' ' -f1 | sort -u))" o user= | sort | uniq -c | sort -rn

And this is where i got with my program. I might be going about it the wrong way and could use a bit of help.

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include <sys/types.h>
#include <unistd.h>
#include <sys/wait.h>
#include <signal.h>

void sig_handler(int signo) {
  if (signo == SIGHUP){
    int pid = 0;
    if (pid = fork() != 0) {
      execl("/bin/ps", "ps", "-u", "\"$(echo $(w -h | cut -d ' ' -f1 | sort -u))\"", "o", "user=", "|", "sort", "|",  "uniq", "-c", "|", "sort", "-rn", NULL);
    } else {
      printf("Signal received: SIGINT\nReported by: Parent process\n\n");
    }
  }
}

int main(void) {
  if (signal(SIGHUP, sig_handler) == SIG_ERR)
    printf("\nCan't catch SIGINT\n");

  while (1)
    sleep(1);
  return 0;
}

Upvotes: 1

Views: 253

Answers (1)

Some programmer dude
Some programmer dude

Reputation: 409166

You need to read about operator precedence. The line

if (pid = fork() != 0) {

does not do what you think it does!

In fact the compiler sees it as

if (pid = (fork() != 0)) {

This means, among other things, that you run the execl in the parent process, and not the child which is customary.


As for your problem, it's because you try to run shell-specific things (embedded commands, piping etc.) but you're not actually running a shell.

Either you have to exec a shell, or use the e.g. the system function.

Upvotes: 2

Related Questions