kern_xxx.c revision 12221
11541Srgrimes/*
21541Srgrimes * Copyright (c) 1982, 1986, 1989, 1993
31541Srgrimes *	The Regents of the University of California.  All rights reserved.
41541Srgrimes *
51541Srgrimes * Redistribution and use in source and binary forms, with or without
61541Srgrimes * modification, are permitted provided that the following conditions
71541Srgrimes * are met:
81541Srgrimes * 1. Redistributions of source code must retain the above copyright
91541Srgrimes *    notice, this list of conditions and the following disclaimer.
101541Srgrimes * 2. Redistributions in binary form must reproduce the above copyright
111541Srgrimes *    notice, this list of conditions and the following disclaimer in the
121541Srgrimes *    documentation and/or other materials provided with the distribution.
131541Srgrimes * 3. All advertising materials mentioning features or use of this software
141541Srgrimes *    must display the following acknowledgement:
151541Srgrimes *	This product includes software developed by the University of
161541Srgrimes *	California, Berkeley and its contributors.
171541Srgrimes * 4. Neither the name of the University nor the names of its contributors
181541Srgrimes *    may be used to endorse or promote products derived from this software
191541Srgrimes *    without specific prior written permission.
201541Srgrimes *
211541Srgrimes * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
221541Srgrimes * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
231541Srgrimes * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
241541Srgrimes * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
251541Srgrimes * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
261541Srgrimes * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
271541Srgrimes * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
281541Srgrimes * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
291541Srgrimes * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
301541Srgrimes * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
311541Srgrimes * SUCH DAMAGE.
321541Srgrimes *
331541Srgrimes *	@(#)kern_xxx.c	8.2 (Berkeley) 11/14/93
3412221Sbde * $Id: kern_xxx.c,v 1.16 1995/11/11 01:04:42 bde Exp $
351541Srgrimes */
361541Srgrimes
371541Srgrimes#include <sys/param.h>
381541Srgrimes#include <sys/systm.h>
3912221Sbde#include <sys/sysproto.h>
401541Srgrimes#include <sys/kernel.h>
411541Srgrimes#include <sys/proc.h>
421541Srgrimes#include <sys/reboot.h>
431541Srgrimes#include <vm/vm.h>
441541Srgrimes#include <sys/sysctl.h>
451549Srgrimes#include <sys/utsname.h>
463308Sphk#include <sys/signalvar.h>
471541Srgrimes
484959Sphk/* This implements a "TEXT_SET" for cleanup functions */
494959Sphk
504959Sphkstatic void
514959Sphkdummy_cleanup() {}
524959SphkTEXT_SET(cleanup_set, dummy_cleanup);
538876Srgrimes
544959Sphktypedef void (*cleanup_func_t)(void);
554959Sphkextern const struct linker_set cleanup_set;
564959Sphkstatic const cleanup_func_t *cleanups =
574959Sphk        (const cleanup_func_t *)&cleanup_set.ls_items[0];
584959Sphk
5912221Sbde#ifndef _SYS_SYSPROTO_H_
601541Srgrimesstruct reboot_args {
611541Srgrimes	int	opt;
621541Srgrimes};
6312221Sbde#endif
641541Srgrimes/* ARGSUSED */
651549Srgrimesint
661541Srgrimesreboot(p, uap, retval)
671541Srgrimes	struct proc *p;
681541Srgrimes	struct reboot_args *uap;
691541Srgrimes	int *retval;
701541Srgrimes{
711541Srgrimes	int error;
721541Srgrimes
733098Sphk	if ((error = suser(p->p_ucred, &p->p_acflag)))
741541Srgrimes		return (error);
754959Sphk
764959Sphk	if (!uap->opt & RB_NOSYNC) {
774959Sphk		printf("\ncleaning up... ");
784959Sphk                while(*cleanups) {
794959Sphk                        (**cleanups++)();
804959Sphk                }
814959Sphk	}
824959Sphk
831541Srgrimes	boot(uap->opt);
841541Srgrimes	return (0);
851541Srgrimes}
861541Srgrimes
871541Srgrimes#if defined(COMPAT_43) || defined(COMPAT_SUNOS)
881541Srgrimes
8912221Sbde#ifndef _SYS_SYSPROTO_H_
901541Srgrimesstruct gethostname_args {
911541Srgrimes	char	*hostname;
921541Srgrimes	u_int	len;
931541Srgrimes};
9412221Sbde#endif
951541Srgrimes/* ARGSUSED */
961549Srgrimesint
971541Srgrimesogethostname(p, uap, retval)
981541Srgrimes	struct proc *p;
991541Srgrimes	struct gethostname_args *uap;
1001541Srgrimes	int *retval;
1011541Srgrimes{
10212171Sphk	int name[2];
1031541Srgrimes
10412171Sphk	name[0] = CTL_KERN;
10512171Sphk	name[1] = KERN_HOSTNAME;
10612171Sphk	return (userland_sysctl(p, name, 2, uap->hostname, &uap->len,
10712171Sphk		1, 0, 0, 0));
1081541Srgrimes}
1091541Srgrimes
11012221Sbde#ifndef _SYS_SYSPROTO_H_
1111541Srgrimesstruct sethostname_args {
1121541Srgrimes	char	*hostname;
1131541Srgrimes	u_int	len;
1141541Srgrimes};
11512221Sbde#endif
1161541Srgrimes/* ARGSUSED */
1171549Srgrimesint
1181541Srgrimesosethostname(p, uap, retval)
1191541Srgrimes	struct proc *p;
1201541Srgrimes	register struct sethostname_args *uap;
1211541Srgrimes	int *retval;
1221541Srgrimes{
12312171Sphk	int name[2];
1241541Srgrimes	int error;
1251541Srgrimes
12612171Sphk	name[0] = CTL_KERN;
12712171Sphk	name[1] = KERN_HOSTNAME;
1283098Sphk	if ((error = suser(p->p_ucred, &p->p_acflag)))
1291541Srgrimes		return (error);
13012171Sphk	return (userland_sysctl(p, name, 2, 0, 0, 0,
13112171Sphk		uap->hostname, uap->len, 0));
1321541Srgrimes}
1331541Srgrimes
13412221Sbde#ifndef _SYS_SYSPROTO_H_
13512200Sbdestruct ogethostid_args {
1361541Srgrimes	int	dummy;
1371541Srgrimes};
13812221Sbde#endif
1391541Srgrimes/* ARGSUSED */
1401549Srgrimesint
1411541Srgrimesogethostid(p, uap, retval)
1421541Srgrimes	struct proc *p;
14312200Sbde	struct ogethostid_args *uap;
1441541Srgrimes	int *retval;
1451541Srgrimes{
1461541Srgrimes
1471541Srgrimes	*(long *)retval = hostid;
1481541Srgrimes	return (0);
1491541Srgrimes}
1501541Srgrimes#endif /* COMPAT_43 || COMPAT_SUNOS */
1511541Srgrimes
1521541Srgrimes#ifdef COMPAT_43
15312221Sbde#ifndef _SYS_SYSPROTO_H_
15412200Sbdestruct osethostid_args {
1551541Srgrimes	long	hostid;
1561541Srgrimes};
15712221Sbde#endif
1581541Srgrimes/* ARGSUSED */
1591549Srgrimesint
1601541Srgrimesosethostid(p, uap, retval)
1611541Srgrimes	struct proc *p;
16212200Sbde	struct osethostid_args *uap;
1631541Srgrimes	int *retval;
1641541Srgrimes{
1651541Srgrimes	int error;
1661541Srgrimes
1673098Sphk	if ((error = suser(p->p_ucred, &p->p_acflag)))
1681541Srgrimes		return (error);
1691541Srgrimes	hostid = uap->hostid;
1701541Srgrimes	return (0);
1711541Srgrimes}
1721541Srgrimes
1731549Srgrimesint
17412200Sbdeoquota(p, uap, retval)
17512200Sbde	struct proc *p;
17612200Sbde	struct oquota_args *uap;
17712200Sbde	int *retval;
1781541Srgrimes{
1791541Srgrimes
1801541Srgrimes	return (ENOSYS);
1811541Srgrimes}
1821541Srgrimes#endif /* COMPAT_43 */
1831549Srgrimes
1841549Srgrimesvoid
1851549Srgrimesshutdown_nice(void)
1861549Srgrimes{
1871549Srgrimes	/* Send a signal to init(8) and have it shutdown the world */
18810127Sdg	if (initproc != NULL) {
1899798Sdg		psignal(initproc, SIGINT);
19010127Sdg	} else {
19110127Sdg		/* No init(8) running, so simply reboot */
19210127Sdg		boot(RB_NOSYNC);
19310127Sdg	}
1941549Srgrimes	return;
1951549Srgrimes}
1961549Srgrimes
1971549Srgrimes
19812221Sbde#ifndef _SYS_SYSPROTO_H_
1991549Srgrimesstruct uname_args {
2001549Srgrimes        struct utsname  *name;
2011549Srgrimes};
20212221Sbde#endif
2031549Srgrimes
2041549Srgrimes/* ARGSUSED */
2051549Srgrimesint
2061549Srgrimesuname(p, uap, retval)
2071549Srgrimes	struct proc *p;
2081549Srgrimes	struct uname_args *uap;
2091549Srgrimes	int *retval;
2101549Srgrimes{
21112171Sphk	int name[2], len, rtval, junk;
2121549Srgrimes	char *s, *us;
2131549Srgrimes
21412171Sphk	name[0] = CTL_KERN;
21512171Sphk	name[1] = KERN_OSTYPE;
2161549Srgrimes	len = sizeof uap->name->sysname;
21712171Sphk	rtval = userland_sysctl(p, name, 2, uap->name->sysname, &len,
21812171Sphk		1, 0, 0, 0);
2191549Srgrimes	if( rtval) return rtval;
2201549Srgrimes	subyte( uap->name->sysname + sizeof(uap->name->sysname) - 1, 0);
2211549Srgrimes
22212171Sphk	name[1] = KERN_HOSTNAME;
2231549Srgrimes	len = sizeof uap->name->nodename;
22412171Sphk	rtval = userland_sysctl(p, name, 2, uap->name->nodename, &len,
22512171Sphk		1, 0, 0, 0);
2261549Srgrimes	if( rtval) return rtval;
2271549Srgrimes	subyte( uap->name->nodename + sizeof(uap->name->nodename) - 1, 0);
2281549Srgrimes
22912171Sphk	name[1] = KERN_OSRELEASE;
2301549Srgrimes	len = sizeof uap->name->release;
23112171Sphk	rtval = userland_sysctl(p, name, 2, uap->name->release, &len,
23212171Sphk		1, 0, 0, 0);
2331549Srgrimes	if( rtval) return rtval;
2341549Srgrimes	subyte( uap->name->release + sizeof(uap->name->release) - 1, 0);
2351549Srgrimes
2361549Srgrimes/*
2371549Srgrimes	name = KERN_VERSION;
2381549Srgrimes	len = sizeof uap->name->version;
23912171Sphk	rtval = userland_sysctl(p, name, 2, uap->name->version, &len,
24012171Sphk		1, 0, 0, 0);
2411549Srgrimes	if( rtval) return rtval;
2421549Srgrimes	subyte( uap->name->version + sizeof(uap->name->version) - 1, 0);
2431549Srgrimes*/
2441549Srgrimes
2451549Srgrimes/*
2461549Srgrimes * this stupid hackery to make the version field look like FreeBSD 1.1
2471549Srgrimes */
2481549Srgrimes	for(s = version; *s && *s != '#'; s++);
2491549Srgrimes
2501549Srgrimes	for(us = uap->name->version; *s && *s != ':'; s++) {
2511549Srgrimes		rtval = subyte( us++, *s);
2521549Srgrimes		if( rtval)
2531549Srgrimes			return rtval;
2541549Srgrimes	}
2551549Srgrimes	rtval = subyte( us++, 0);
2561549Srgrimes	if( rtval)
2571549Srgrimes		return rtval;
2581549Srgrimes
25912171Sphk	name[1] = HW_MACHINE;
2601549Srgrimes	len = sizeof uap->name->machine;
26112171Sphk	rtval = userland_sysctl(p, name, 2, uap->name->machine, &len,
26212171Sphk		1, 0, 0, 0);
2631549Srgrimes	if( rtval) return rtval;
2641549Srgrimes	subyte( uap->name->machine + sizeof(uap->name->machine) - 1, 0);
2651549Srgrimes
2661549Srgrimes	return 0;
2671549Srgrimes}
2681549Srgrimes
26912221Sbde#ifndef _SYS_SYSPROTO_H_
2701549Srgrimesstruct getdomainname_args {
2711549Srgrimes        char    *domainname;
2721549Srgrimes        u_int   len;
2731549Srgrimes};
2741549Srgrimes
27512221Sbde#endif
2761549Srgrimes/* ARGSUSED */
2771549Srgrimesint
2781549Srgrimesgetdomainname(p, uap, retval)
2791549Srgrimes        struct proc *p;
2801549Srgrimes        struct getdomainname_args *uap;
2811549Srgrimes        int *retval;
2821549Srgrimes{
2831549Srgrimes	if (uap->len > domainnamelen + 1)
2841549Srgrimes		uap->len = domainnamelen + 1;
2851549Srgrimes	return (copyout((caddr_t)domainname, (caddr_t)uap->domainname, uap->len));
2861549Srgrimes}
2871549Srgrimes
28812221Sbde#ifndef _SYS_SYSPROTO_H_
2891549Srgrimesstruct setdomainname_args {
2901549Srgrimes        char    *domainname;
2911549Srgrimes        u_int   len;
2921549Srgrimes};
29312221Sbde#endif
2941549Srgrimes
2951549Srgrimes/* ARGSUSED */
2961549Srgrimesint
2971549Srgrimessetdomainname(p, uap, retval)
2981549Srgrimes        struct proc *p;
2991549Srgrimes        struct setdomainname_args *uap;
3001549Srgrimes        int *retval;
3011549Srgrimes{
3021549Srgrimes        int error;
3031549Srgrimes
3043098Sphk        if ((error = suser(p->p_ucred, &p->p_acflag)))
3051549Srgrimes                return (error);
3061549Srgrimes        if (uap->len > sizeof (domainname) - 1)
3071549Srgrimes                return EINVAL;
3081549Srgrimes        domainnamelen = uap->len;
3091549Srgrimes        error = copyin((caddr_t)uap->domainname, domainname, uap->len);
3101549Srgrimes        domainname[domainnamelen] = 0;
3111549Srgrimes        return (error);
3121549Srgrimes}
3131549Srgrimes
314