1/* nproc - print the number of processors.
2   Copyright (C) 2009-2010 Free Software Foundation, Inc.
3
4   This program is free software: you can redistribute it and/or modify
5   it under the terms of the GNU General Public License as published by
6   the Free Software Foundation, either version 3 of the License, or
7   (at your option) any later version.
8
9   This program is distributed in the hope that it will be useful,
10   but WITHOUT ANY WARRANTY; without even the implied warranty of
11   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12   GNU General Public License for more details.
13
14   You should have received a copy of the GNU General Public License
15   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
16
17/* Written by Giuseppe Scrivano.  */
18
19#include <config.h>
20#include <getopt.h>
21#include <stdio.h>
22#include <sys/types.h>
23
24#include "system.h"
25#include "error.h"
26#include "nproc.h"
27#include "xstrtol.h"
28
29/* The official name of this program (e.g., no `g' prefix).  */
30#define PROGRAM_NAME "nproc"
31
32#define AUTHORS proper_name ("Giuseppe Scrivano")
33
34enum
35{
36  ALL_OPTION = CHAR_MAX + 1,
37  IGNORE_OPTION
38};
39
40static struct option const longopts[] =
41{
42  {"all", no_argument, NULL, ALL_OPTION},
43  {"ignore", required_argument, NULL, IGNORE_OPTION},
44  {GETOPT_HELP_OPTION_DECL},
45  {GETOPT_VERSION_OPTION_DECL},
46  {NULL, 0, NULL, 0}
47};
48
49void
50usage (int status)
51{
52  if (status != EXIT_SUCCESS)
53    fprintf (stderr, _("Try `%s --help' for more information.\n"),
54             program_name);
55  else
56    {
57      printf (_("Usage: %s [OPTION]...\n"), program_name);
58      fputs (_("\
59Print the number of processing units available to the current process,\n\
60which may be less than the number of online processors\n\
61\n\
62"), stdout);
63      fputs (_("\
64     --all       print the number of installed processors\n\
65     --ignore=N  if possible, exclude N processing units\n\
66"), stdout);
67
68      fputs (HELP_OPTION_DESCRIPTION, stdout);
69      fputs (VERSION_OPTION_DESCRIPTION, stdout);
70      emit_ancillary_info ();
71    }
72  exit (status);
73}
74
75int
76main (int argc, char **argv)
77{
78  unsigned long nproc, ignore = 0;
79  enum nproc_query mode;
80  initialize_main (&argc, &argv);
81  set_program_name (argv[0]);
82  setlocale (LC_ALL, "");
83  bindtextdomain (PACKAGE, LOCALEDIR);
84  textdomain (PACKAGE);
85
86  atexit (close_stdout);
87
88  mode = NPROC_CURRENT_OVERRIDABLE;
89
90  while (1)
91    {
92      int c = getopt_long (argc, argv, "", longopts, NULL);
93      if (c == -1)
94        break;
95      switch (c)
96        {
97        case_GETOPT_HELP_CHAR;
98
99        case_GETOPT_VERSION_CHAR (PROGRAM_NAME, AUTHORS);
100
101        case ALL_OPTION:
102          mode = NPROC_ALL;
103          break;
104
105        case IGNORE_OPTION:
106          if (xstrtoul (optarg, NULL, 10, &ignore, "") != LONGINT_OK)
107            {
108              error (0, 0, _("%s: invalid number to ignore"), optarg);
109              usage (EXIT_FAILURE);
110            }
111          break;
112
113        default:
114          usage (EXIT_FAILURE);
115        }
116    }
117
118  nproc = num_processors (mode);
119
120  if (ignore < nproc)
121    nproc -= ignore;
122  else
123    nproc = 1;
124
125  printf ("%lu\n", nproc);
126
127  exit (EXIT_SUCCESS);
128}
129