1 /*********************************************************************** 2 * * 3 * This software is part of the ast package * 4 * Copyright (c) 1992-2007 AT&T Knowledge Ventures * 5 * and is licensed under the * 6 * Common Public License, Version 1.0 * 7 * by AT&T Knowledge Ventures * 8 * * 9 * A copy of the License is available at * 10 * http://www.opensource.org/licenses/cpl1.0.txt * 11 * (with md5 checksum 059e8cd6165cb4c31e351f2b69388fd9) * 12 * * 13 * Information and Software Systems Research * 14 * AT&T Research * 15 * Florham Park NJ * 16 * * 17 * Glenn Fowler <gsf@research.att.com> * 18 * David Korn <dgk@research.att.com> * 19 * * 20 ***********************************************************************/ 21 #pragma prototyped 22 /* 23 * David Korn 24 * Glenn Fowler 25 * AT&T Research 26 * 27 * uname 28 */ 29 30 static const char usage[] = 31 "[-?\n@(#)$Id: uname (AT&T Research) 2007-01-22 $\n]" 32 USAGE_LICENSE 33 "[+NAME?uname - identify the current system ]" 34 "[+DESCRIPTION?By default \buname\b writes the operating system name to" 35 " standard output. When options are specified, one or more" 36 " system characteristics are written to standard output, space" 37 " separated, on a single line. When more than one option is specifed" 38 " the output is in the order specfied by the \b-A\b option below." 39 " Unsupported option values are listed as \a[option]]\a. If any unknown" 40 " options are specified then the local \b/usr/bin/uname\b is called.]" 41 "[+?If any \aname\a operands are specified then the \bsysinfo\b(2) values" 42 " for each \aname\a are listed, separated by space, on one line." 43 " \bgetconf\b(1), a pre-existing \astandard\a interface, provides" 44 " access to the same information; vendors should spend more time" 45 " using standards than inventing them.]" 46 "[+?Selected information is printed in the same order as the options below.]" 47 "[a:all?Equivalent to \b-snrvmpio\b.]" 48 "[s:system|sysname|kernel-name?The detailed kernel name. This is the default.]" 49 "[n:nodename?The hostname or nodename.]" 50 "[r:release|kernel-release?The kernel release level.]" 51 "[v:version|kernel-version?The kernel version level.]" 52 "[m:machine?The name of the hardware type the system is running on.]" 53 "[p:processor?The name of the processor instruction set architecture.]" 54 "[i:implementation|platform|hardware-platform?The hardware implementation;" 55 " this is \b--host-id\b on some systems.]" 56 "[o:operating-system?The generic operating system name.]" 57 "[h:host-id|id?The host id in hex.]" 58 "[d:domain?The domain name returned by \agetdomainname\a(2).]" 59 "[R:extended-release?The extended release name.]" 60 "[A:everything?Equivalent to \b-snrvmpiohdR\b.]" 61 "[f:list?List all \bsysinfo\b(2) names and values, one per line.]" 62 "[S:sethost?Set the hostname or nodename to \aname\a. No output is" 63 " written to standard output.]:[name]" 64 65 "[+SEE ALSO?\bhostname\b(1), \bgetconf\b(1), \buname\b(2)," 66 " \bsysconf\b(2), \bsysinfo\b(2)]" 67 ; 68 69 #if defined(__STDPP__directive) && defined(__STDPP__hide) 70 __STDPP__directive pragma pp:hide getdomainname gethostid gethostname sethostname 71 #else 72 #define getdomainname ______getdomainname 73 #define gethostid ______gethostid 74 #define gethostname ______gethostname 75 #define sethostname ______sethostname 76 #endif 77 78 #include <cmd.h> 79 #include <ctype.h> 80 #include <proc.h> 81 82 #include "FEATURE/utsname" 83 84 #define MAXHOSTNAME 64 85 86 #if _lib_uname && _sys_utsname 87 88 #include <sys/utsname.h> 89 90 #endif 91 92 #if defined(__STDPP__directive) && defined(__STDPP__hide) 93 __STDPP__directive pragma pp:nohide getdomainname gethostid gethostname sethostname 94 #else 95 #undef getdomainname 96 #undef gethostid 97 #undef gethostname 98 #undef sethostname 99 #endif 100 101 #if _lib_getdomainname 102 extern int getdomainname(char*, size_t); 103 #endif 104 #if _lib_gethostid 105 extern int gethostid(void); 106 #endif 107 #if _lib_gethostname 108 extern int gethostname(char*, size_t); 109 #endif 110 #if _lib_sethostname 111 extern int sethostname(const char*, size_t); 112 #endif 113 114 #ifndef HOSTTYPE 115 #define HOSTTYPE "unknown" 116 #endif 117 118 static const char hosttype[] = HOSTTYPE; 119 120 #if !_lib_uname || !_sys_utsname 121 122 #if defined(__STDPP__) 123 #define SYSNAME #(getprd machine) 124 #define RELEASE #(getprd release) 125 #define VERSION #(getprd version) 126 #define MACHINE #(getprd architecture) 127 #else 128 #define SYSNAME "" 129 #define RELEASE "" 130 #define VERSION "" 131 #define MACHINE "" 132 #endif 133 134 struct utsname 135 { 136 char* sysname; 137 char nodename[MAXHOSTNAME]; 138 char* release; 139 char* version; 140 char* machine; 141 }; 142 143 int 144 uname(register struct utsname* ut) 145 { 146 #ifdef HOSTTYPE 147 char* sys = 0; 148 char* arch = 0; 149 150 if (*hosttype) 151 { 152 static char buf[sizeof(hosttype)]; 153 154 strcpy(buf, hosttype); 155 sys = buf; 156 if (arch = strchr(sys, '.')) 157 { 158 *arch++ = 0; 159 if (!*arch) 160 arch = 0; 161 } 162 if (!*sys) 163 sys = 0; 164 } 165 #endif 166 #ifdef _lib_gethostname 167 if (gethostname(ut->nodename, sizeof(ut->nodename) - 1)) 168 return -1; 169 #else 170 strncpy(ut->nodename, "local", sizeof(ut->nodename) - 1); 171 #endif 172 #ifdef HOSTTYPE 173 if (!(ut->sysname = sys)) 174 #endif 175 if (!*(ut->sysname = SYSNAME)) 176 ut->sysname = ut->nodename; 177 #ifdef HOSTTYPE 178 if (!(ut->machine = arch)) 179 #endif 180 ut->machine = MACHINE; 181 ut->release = RELEASE; 182 ut->version = VERSION; 183 return 0; 184 } 185 186 #endif 187 188 #define OPT_system (1<<0) 189 #define OPT_nodename (1<<1) 190 #define OPT_release (1<<2) 191 #define OPT_version (1<<3) 192 #define OPT_machine (1<<4) 193 #define OPT_processor (1<<5) 194 195 #define OPT_STANDARD 6 196 197 #define OPT_implementation (1<<6) 198 #define OPT_operating_system (1<<7) 199 200 #define OPT_ALL 8 201 202 #define OPT_hostid (1<<8) 203 #define OPT_vendor (1<<9) 204 #define OPT_domain (1<<10) 205 #define OPT_machine_type (1<<11) 206 #define OPT_base (1<<12) 207 #define OPT_extended_release (1<<13) 208 #define OPT_extra (1<<14) 209 210 #define OPT_TOTAL 15 211 212 #define OPT_all (1L<<29) 213 #define OPT_total (1L<<30) 214 #define OPT_standard ((1<<OPT_STANDARD)-1) 215 216 #ifndef MACHINE 217 #if defined(__STDPP__) 218 #define MACHINE #(getprd architecture) 219 #else 220 #define MACHINE "" 221 #endif 222 #endif 223 224 #ifndef HOSTTYPE 225 #define HOSTTYPE "unknown" 226 #endif 227 228 #define extra(m) do \ 229 { \ 230 if ((char*)&ut.m[sizeof(ut.m)] > last) \ 231 last = (char*)&ut.m[sizeof(ut.m)]; \ 232 } while(0) 233 234 #define output(f,v,u) do \ 235 { \ 236 if ((flags&(f))&&(*(v)||(flags&(OPT_all|OPT_total))==OPT_all&&((f)&OPT_standard)||!(flags&(OPT_all|OPT_total)))) \ 237 { \ 238 if (sep) \ 239 sfputc(sfstdout, ' '); \ 240 else \ 241 sep = 1; \ 242 if (*(v)) \ 243 sfputr(sfstdout, v, -1); \ 244 else \ 245 sfprintf(sfstdout, "[%s]", u); \ 246 } \ 247 } while (0) 248 249 int 250 b_uname(int argc, char** argv, void* context) 251 { 252 register long flags = 0; 253 register int sep = 0; 254 register int n; 255 register char* s; 256 char* t; 257 char* e; 258 char* sethost = 0; 259 int list = 0; 260 struct utsname ut; 261 char buf[257]; 262 263 cmdinit(argc, argv, context, ERROR_CATALOG, 0); 264 for (;;) 265 { 266 switch (optget(argv, usage)) 267 { 268 case 'a': 269 flags |= OPT_all|((1L<<OPT_ALL)-1); 270 continue; 271 case 'b': 272 flags |= OPT_base; 273 continue; 274 case 'c': 275 flags |= OPT_vendor; 276 continue; 277 case 'd': 278 flags |= OPT_domain; 279 continue; 280 case 'f': 281 list = 1; 282 continue; 283 case 'h': 284 flags |= OPT_hostid; 285 continue; 286 case 'i': 287 flags |= OPT_implementation; 288 continue; 289 case 'm': 290 flags |= OPT_machine; 291 continue; 292 case 'n': 293 flags |= OPT_nodename; 294 continue; 295 case 'o': 296 flags |= OPT_operating_system; 297 continue; 298 case 'p': 299 flags |= OPT_processor; 300 continue; 301 case 'r': 302 flags |= OPT_release; 303 continue; 304 case 's': 305 flags |= OPT_system; 306 continue; 307 case 't': 308 flags |= OPT_machine_type; 309 continue; 310 case 'v': 311 flags |= OPT_version; 312 continue; 313 case 'x': 314 flags |= OPT_extra; 315 continue; 316 case 'A': 317 flags |= OPT_total|((1L<<OPT_TOTAL)-1); 318 continue; 319 case 'R': 320 flags |= OPT_extended_release; 321 continue; 322 case 'S': 323 sethost = opt_info.arg; 324 continue; 325 case ':': 326 s = "/usr/bin/uname"; 327 if (!streq(argv[0], s) && (!eaccess(s, X_OK) || !eaccess(s+=4, X_OK))) 328 { 329 argv[0] = s; 330 return procrun(s, argv); 331 } 332 error(2, "%s", opt_info.arg); 333 break; 334 case '?': 335 error(ERROR_usage(2), "%s", opt_info.arg); 336 break; 337 } 338 break; 339 } 340 argv += opt_info.index; 341 if (error_info.errors || *argv && (flags || sethost) || sethost && flags) 342 error(ERROR_usage(2), "%s", optusage(NiL)); 343 if (sethost) 344 { 345 #if _lib_sethostname 346 if (sethostname(sethost, strlen(sethost) + 1)) 347 #else 348 #ifdef ENOSYS 349 errno = ENOSYS; 350 #else 351 errno = EPERM; 352 #endif 353 #endif 354 error(ERROR_system(1), "%s: cannot set host name", sethost); 355 } 356 else if (list) 357 astconflist(sfstdout, NiL, ASTCONF_base|ASTCONF_defined|ASTCONF_lower|ASTCONF_quote|ASTCONF_matchcall, "CS|SI"); 358 else if (*argv) 359 { 360 e = &buf[sizeof(buf)-1]; 361 while (s = *argv++) 362 { 363 t = buf; 364 *t++ = 'C'; 365 *t++ = 'S'; 366 *t++ = '_'; 367 while (t < e && (n = *s++)) 368 *t++ = islower(n) ? toupper(n) : n; 369 *t = 0; 370 sfprintf(sfstdout, "%s%c", *(t = astconf(buf, NiL, NiL)) ? t : "unknown", *argv ? ' ' : '\n'); 371 } 372 } 373 else 374 { 375 s = buf; 376 if (!flags) 377 flags = OPT_system; 378 memzero(&ut, sizeof(ut)); 379 if (uname(&ut) < 0) 380 error(ERROR_usage(2), "information unavailable"); 381 output(OPT_system, ut.sysname, "sysname"); 382 if (flags & OPT_nodename) 383 { 384 #if !_mem_nodeext_utsname && _lib_gethostname 385 if (sizeof(ut.nodename) > 9 || gethostname(s, sizeof(buf))) 386 #endif 387 s = ut.nodename; 388 output(OPT_nodename, s, "nodename"); 389 } 390 output(OPT_release, ut.release, "release"); 391 output(OPT_version, ut.version, "version"); 392 output(OPT_machine, ut.machine, "machine"); 393 if (flags & OPT_processor) 394 { 395 if (!*(s = astconf("ARCHITECTURE", NiL, NiL))) 396 s = ut.machine; 397 output(OPT_processor, s, "processor"); 398 } 399 if (flags & OPT_implementation) 400 { 401 if (!*(s = astconf("PLATFORM", NiL, NiL)) && !*(s = astconf("HW_NAME", NiL, NiL))) 402 { 403 if (t = strchr(hosttype, '.')) 404 t++; 405 else 406 t = (char*)hosttype; 407 strncpy(s = buf, t, sizeof(buf) - 1); 408 } 409 output(OPT_implementation, s, "implementation"); 410 } 411 if (flags & OPT_operating_system) 412 { 413 s = astconf("OPERATING_SYSTEM", NiL, NiL); 414 if (!*s) 415 #ifdef _UNAME_os_DEFAULT 416 s = _UNAME_os_DEFAULT; 417 #else 418 s = ut.sysname; 419 #endif 420 output(OPT_operating_system, s, "operating-system"); 421 } 422 if (flags & OPT_extended_release) 423 { 424 s = astconf("RELEASE", NiL, NiL); 425 output(OPT_extended_release, s, "extended-release"); 426 } 427 #if _mem_idnumber_utsname 428 output(OPT_hostid, ut.idnumber, "hostid"); 429 #else 430 if (flags & OPT_hostid) 431 { 432 if (!*(s = astconf("HW_SERIAL", NiL, NiL))) 433 #if _lib_gethostid 434 sfsprintf(s = buf, sizeof(buf), "%08x", gethostid()); 435 #else 436 /*NOP*/; 437 #endif 438 output(OPT_hostid, s, "hostid"); 439 } 440 #endif 441 if (flags & OPT_vendor) 442 { 443 s = astconf("HW_PROVIDER", NiL, NiL); 444 output(OPT_vendor, s, "vendor"); 445 } 446 if (flags & OPT_domain) 447 { 448 if (!*(s = astconf("SRPC_DOMAIN", NiL, NiL))) 449 #if _lib_getdomainname 450 getdomainname(s, sizeof(buf)); 451 #else 452 /*NOP*/; 453 #endif 454 output(OPT_domain, s, "domain"); 455 } 456 #if _mem_m_type_utsname 457 s = ut.m_type; 458 #else 459 s = astconf("MACHINE", NiL, NiL); 460 #endif 461 output(OPT_machine_type, s, "m_type"); 462 #if _mem_base_rel_utsname 463 s = ut.base_rel; 464 #else 465 s = astconf("BASE", NiL, NiL); 466 #endif 467 output(OPT_base, s, "base_rel"); 468 if (flags & OPT_extra) 469 { 470 char* last = (char*)&ut; 471 472 extra(sysname); 473 extra(nodename); 474 extra(release); 475 extra(version); 476 extra(machine); 477 #if _mem_idnumber_utsname 478 extra(idnumber); 479 #endif 480 #if _mem_m_type_utsname 481 extra(m_type); 482 #endif 483 #if _mem_base_rel_utsname 484 extra(base_rel); 485 #endif 486 if (last < ((char*)(&ut + 1))) 487 { 488 s = t = last; 489 while (s < (char*)(&ut + 1)) 490 { 491 if (!(n = *s++)) 492 { 493 if ((s - t) > 1) 494 { 495 if (sep) 496 sfputc(sfstdout, ' '); 497 else 498 sep = 1; 499 sfputr(sfstdout, t, -1); 500 } 501 t = s; 502 } 503 else if (!isprint(n)) 504 break; 505 } 506 } 507 } 508 if (sep) 509 sfputc(sfstdout, '\n'); 510 } 511 return error_info.errors; 512 } 513