2002-07-20 02:56:12 +00:00
|
|
|
/*-
|
2017-11-27 15:13:23 +00:00
|
|
|
* SPDX-License-Identifier: BSD-2-Clause-FreeBSD
|
|
|
|
*
|
2002-07-20 02:56:12 +00:00
|
|
|
* Copyright (c) 2002 Doug Rabson
|
|
|
|
* All rights reserved.
|
|
|
|
*
|
|
|
|
* Redistribution and use in source and binary forms, with or without
|
|
|
|
* modification, are permitted provided that the following conditions
|
|
|
|
* are met:
|
|
|
|
* 1. Redistributions of source code must retain the above copyright
|
|
|
|
* notice, this list of conditions and the following disclaimer.
|
|
|
|
* 2. Redistributions in binary form must reproduce the above copyright
|
|
|
|
* notice, this list of conditions and the following disclaimer in the
|
|
|
|
* documentation and/or other materials provided with the distribution.
|
|
|
|
*
|
|
|
|
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
|
|
|
|
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
|
|
|
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
|
|
|
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
|
|
|
|
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
|
|
|
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
|
|
|
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
|
|
|
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
|
|
|
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
|
|
|
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
|
|
|
* SUCH DAMAGE.
|
|
|
|
*/
|
|
|
|
|
2003-07-25 21:19:19 +00:00
|
|
|
#include <sys/cdefs.h>
|
|
|
|
__FBSDID("$FreeBSD$");
|
|
|
|
|
2009-04-29 21:14:15 +00:00
|
|
|
#include "opt_inet.h"
|
|
|
|
#include "opt_inet6.h"
|
2017-11-25 04:49:12 +00:00
|
|
|
#include "opt_ktrace.h"
|
2002-10-09 22:27:24 +00:00
|
|
|
|
2010-03-11 14:49:06 +00:00
|
|
|
#define __ELF_WORD_SIZE 32
|
|
|
|
|
2017-11-25 04:49:12 +00:00
|
|
|
#ifdef COMPAT_FREEBSD11
|
|
|
|
#define _WANT_FREEBSD11_KEVENT
|
|
|
|
#endif
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
#include <sys/param.h>
|
|
|
|
#include <sys/bus.h>
|
2014-03-16 10:55:57 +00:00
|
|
|
#include <sys/capsicum.h>
|
2006-10-02 12:59:59 +00:00
|
|
|
#include <sys/clock.h>
|
2002-07-20 02:56:12 +00:00
|
|
|
#include <sys/exec.h>
|
|
|
|
#include <sys/fcntl.h>
|
|
|
|
#include <sys/filedesc.h>
|
|
|
|
#include <sys/imgact.h>
|
MFp4:
Bring in updated jail support from bz_jail branch.
This enhances the current jail implementation to permit multiple
addresses per jail. In addtion to IPv4, IPv6 is supported as well.
Due to updated checks it is even possible to have jails without
an IP address at all, which basically gives one a chroot with
restricted process view, no networking,..
SCTP support was updated and supports IPv6 in jails as well.
Cpuset support permits jails to be bound to specific processor
sets after creation.
Jails can have an unrestricted (no duplicate protection, etc.) name
in addition to the hostname. The jail name cannot be changed from
within a jail and is considered to be used for management purposes
or as audit-token in the future.
DDB 'show jails' command was added to aid debugging.
Proper compat support permits 32bit jail binaries to be used on 64bit
systems to manage jails. Also backward compatibility was preserved where
possible: for jail v1 syscalls, as well as with user space management
utilities.
Both jail as well as prison version were updated for the new features.
A gap was intentionally left as the intermediate versions had been
used by various patches floating around the last years.
Bump __FreeBSD_version for the afore mentioned and in kernel changes.
Special thanks to:
- Pawel Jakub Dawidek (pjd) for his multi-IPv4 patches
and Olivier Houchard (cognet) for initial single-IPv6 patches.
- Jeff Roberson (jeff) and Randall Stewart (rrs) for their
help, ideas and review on cpuset and SCTP support.
- Robert Watson (rwatson) for lots and lots of help, discussions,
suggestions and review of most of the patch at various stages.
- John Baldwin (jhb) for his help.
- Simon L. Nielsen (simon) as early adopter testing changes
on cluster machines as well as all the testers and people
who provided feedback the last months on freebsd-jail and
other channels.
- My employer, CK Software GmbH, for the support so I could work on this.
Reviewed by: (see above)
MFC after: 3 months (this is just so that I get the mail)
X-MFC Before: 7.2-RELEASE if possible
2008-11-29 14:32:14 +00:00
|
|
|
#include <sys/jail.h>
|
2002-07-20 02:56:12 +00:00
|
|
|
#include <sys/kernel.h>
|
2006-08-16 00:02:36 +00:00
|
|
|
#include <sys/limits.h>
|
2011-03-30 14:46:12 +00:00
|
|
|
#include <sys/linker.h>
|
2002-07-20 02:56:12 +00:00
|
|
|
#include <sys/lock.h>
|
|
|
|
#include <sys/malloc.h>
|
|
|
|
#include <sys/file.h> /* Must come after sys/malloc.h */
|
2010-03-11 14:49:06 +00:00
|
|
|
#include <sys/imgact.h>
|
2005-10-31 21:09:56 +00:00
|
|
|
#include <sys/mbuf.h>
|
2002-07-20 02:56:12 +00:00
|
|
|
#include <sys/mman.h>
|
|
|
|
#include <sys/module.h>
|
|
|
|
#include <sys/mount.h>
|
|
|
|
#include <sys/mutex.h>
|
2008-09-15 17:39:40 +00:00
|
|
|
#include <sys/namei.h>
|
2002-07-20 02:56:12 +00:00
|
|
|
#include <sys/proc.h>
|
2013-09-19 18:53:42 +00:00
|
|
|
#include <sys/procctl.h>
|
2002-07-20 02:56:12 +00:00
|
|
|
#include <sys/reboot.h>
|
|
|
|
#include <sys/resource.h>
|
|
|
|
#include <sys/resourcevar.h>
|
|
|
|
#include <sys/selinfo.h>
|
2005-06-03 23:15:01 +00:00
|
|
|
#include <sys/eventvar.h> /* Must come after sys/selinfo.h */
|
2002-07-20 02:56:12 +00:00
|
|
|
#include <sys/pipe.h> /* Must come after sys/selinfo.h */
|
|
|
|
#include <sys/signal.h>
|
|
|
|
#include <sys/signalvar.h>
|
|
|
|
#include <sys/socket.h>
|
|
|
|
#include <sys/socketvar.h>
|
|
|
|
#include <sys/stat.h>
|
2005-10-03 18:34:17 +00:00
|
|
|
#include <sys/syscall.h>
|
2003-04-22 18:23:49 +00:00
|
|
|
#include <sys/syscallsubr.h>
|
2002-07-20 02:56:12 +00:00
|
|
|
#include <sys/sysctl.h>
|
|
|
|
#include <sys/sysent.h>
|
|
|
|
#include <sys/sysproto.h>
|
2008-09-15 17:39:40 +00:00
|
|
|
#include <sys/systm.h>
|
2006-09-22 15:04:28 +00:00
|
|
|
#include <sys/thr.h>
|
2002-07-20 02:56:12 +00:00
|
|
|
#include <sys/unistd.h>
|
2006-09-22 15:04:28 +00:00
|
|
|
#include <sys/ucontext.h>
|
2002-07-20 02:56:12 +00:00
|
|
|
#include <sys/vnode.h>
|
2004-03-17 20:00:00 +00:00
|
|
|
#include <sys/wait.h>
|
2006-03-30 07:42:32 +00:00
|
|
|
#include <sys/ipc.h>
|
2007-12-06 23:35:29 +00:00
|
|
|
#include <sys/msg.h>
|
|
|
|
#include <sys/sem.h>
|
2006-03-30 07:42:32 +00:00
|
|
|
#include <sys/shm.h>
|
2017-11-25 04:49:12 +00:00
|
|
|
#ifdef KTRACE
|
|
|
|
#include <sys/ktrace.h>
|
|
|
|
#endif
|
2002-07-20 02:56:12 +00:00
|
|
|
|
2009-04-29 21:14:15 +00:00
|
|
|
#ifdef INET
|
|
|
|
#include <netinet/in.h>
|
|
|
|
#endif
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
#include <vm/vm.h>
|
|
|
|
#include <vm/vm_param.h>
|
|
|
|
#include <vm/pmap.h>
|
|
|
|
#include <vm/vm_map.h>
|
|
|
|
#include <vm/vm_object.h>
|
|
|
|
#include <vm/vm_extern.h>
|
|
|
|
|
2005-10-23 10:43:14 +00:00
|
|
|
#include <machine/cpu.h>
|
2010-03-11 14:49:06 +00:00
|
|
|
#include <machine/elf.h>
|
2019-02-09 03:51:51 +00:00
|
|
|
#ifdef __amd64__
|
|
|
|
#include <machine/md_var.h>
|
|
|
|
#endif
|
2005-10-23 10:43:14 +00:00
|
|
|
|
2008-09-19 15:17:32 +00:00
|
|
|
#include <security/audit/audit.h>
|
|
|
|
|
2003-08-22 23:07:28 +00:00
|
|
|
#include <compat/freebsd32/freebsd32_util.h>
|
|
|
|
#include <compat/freebsd32/freebsd32.h>
|
2007-12-06 23:23:16 +00:00
|
|
|
#include <compat/freebsd32/freebsd32_ipc.h>
|
2013-08-18 13:34:11 +00:00
|
|
|
#include <compat/freebsd32/freebsd32_misc.h>
|
2006-10-05 01:56:11 +00:00
|
|
|
#include <compat/freebsd32/freebsd32_signal.h>
|
2003-08-22 23:07:28 +00:00
|
|
|
#include <compat/freebsd32/freebsd32_proto.h>
|
|
|
|
|
2013-05-31 21:43:17 +00:00
|
|
|
FEATURE(compat_freebsd_32bit, "Compatible with 32-bit FreeBSD");
|
|
|
|
|
2017-06-27 01:29:10 +00:00
|
|
|
#ifdef __amd64__
|
2003-10-30 02:40:30 +00:00
|
|
|
CTASSERT(sizeof(struct timeval32) == 8);
|
|
|
|
CTASSERT(sizeof(struct timespec32) == 8);
|
2007-12-06 23:11:27 +00:00
|
|
|
CTASSERT(sizeof(struct itimerval32) == 16);
|
2017-09-07 04:29:57 +00:00
|
|
|
CTASSERT(sizeof(struct bintime32) == 12);
|
2012-03-03 08:19:18 +00:00
|
|
|
#endif
|
2003-10-30 02:40:30 +00:00
|
|
|
CTASSERT(sizeof(struct statfs32) == 256);
|
2017-06-27 01:29:10 +00:00
|
|
|
#ifdef __amd64__
|
2003-10-30 02:40:30 +00:00
|
|
|
CTASSERT(sizeof(struct rusage32) == 72);
|
2012-03-03 08:19:18 +00:00
|
|
|
#endif
|
2007-12-06 23:11:27 +00:00
|
|
|
CTASSERT(sizeof(struct sigaltstack32) == 12);
|
2017-07-01 22:52:17 +00:00
|
|
|
#ifdef __amd64__
|
Add abstime kqueue(2) timers and expand struct kevent members.
This change implements NOTE_ABSTIME flag for EVFILT_TIMER, which
specifies that the data field contains absolute time to fire the
event.
To make this useful, data member of the struct kevent must be extended
to 64bit. Using the opportunity, I also added ext members. This
changes struct kevent almost to Apple struct kevent64, except I did
not changed type of ident and udata, the later would cause serious API
incompatibilities.
The type of ident was kept uintptr_t since EVFILT_AIO returns a
pointer in this field, and e.g. CHERI is sensitive to the type
(discussed with brooks, jhb).
Unlike Apple kevent64, symbol versioning allows us to claim ABI
compatibility and still name the new syscall kevent(2). Compat shims
are provided for both host native and compat32.
Requested by: bapt
Reviewed by: bapt, brooks, ngie (previous version)
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D11025
2017-06-17 00:57:26 +00:00
|
|
|
CTASSERT(sizeof(struct kevent32) == 56);
|
2017-07-01 22:52:17 +00:00
|
|
|
#else
|
|
|
|
CTASSERT(sizeof(struct kevent32) == 64);
|
2017-06-30 16:12:57 +00:00
|
|
|
#endif
|
2007-12-06 23:11:27 +00:00
|
|
|
CTASSERT(sizeof(struct iovec32) == 8);
|
|
|
|
CTASSERT(sizeof(struct msghdr32) == 28);
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
#ifdef __amd64__
|
|
|
|
CTASSERT(sizeof(struct stat32) == 208);
|
|
|
|
CTASSERT(sizeof(struct freebsd11_stat32) == 96);
|
2012-03-03 08:19:18 +00:00
|
|
|
#endif
|
2007-12-06 23:11:27 +00:00
|
|
|
CTASSERT(sizeof(struct sigaction32) == 24);
|
|
|
|
|
|
|
|
static int freebsd32_kevent_copyout(void *arg, struct kevent *kevp, int count);
|
|
|
|
static int freebsd32_kevent_copyin(void *arg, struct kevent *kevp, int count);
|
2017-03-19 00:51:12 +00:00
|
|
|
static int freebsd32_user_clock_nanosleep(struct thread *td, clockid_t clock_id,
|
|
|
|
int flags, const struct timespec32 *ua_rqtp, struct timespec32 *ua_rmtp);
|
2003-10-30 02:40:30 +00:00
|
|
|
|
2010-04-21 19:28:01 +00:00
|
|
|
void
|
|
|
|
freebsd32_rusage_out(const struct rusage *s, struct rusage32 *s32)
|
|
|
|
{
|
|
|
|
|
|
|
|
TV_CP(*s, *s32, ru_utime);
|
|
|
|
TV_CP(*s, *s32, ru_stime);
|
|
|
|
CP(*s, *s32, ru_maxrss);
|
|
|
|
CP(*s, *s32, ru_ixrss);
|
|
|
|
CP(*s, *s32, ru_idrss);
|
|
|
|
CP(*s, *s32, ru_isrss);
|
|
|
|
CP(*s, *s32, ru_minflt);
|
|
|
|
CP(*s, *s32, ru_majflt);
|
|
|
|
CP(*s, *s32, ru_nswap);
|
|
|
|
CP(*s, *s32, ru_inblock);
|
|
|
|
CP(*s, *s32, ru_oublock);
|
|
|
|
CP(*s, *s32, ru_msgsnd);
|
|
|
|
CP(*s, *s32, ru_msgrcv);
|
|
|
|
CP(*s, *s32, ru_nsignals);
|
|
|
|
CP(*s, *s32, ru_nvcsw);
|
|
|
|
CP(*s, *s32, ru_nivcsw);
|
|
|
|
}
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_wait4(struct thread *td, struct freebsd32_wait4_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2004-03-17 20:00:00 +00:00
|
|
|
int error, status;
|
|
|
|
struct rusage32 ru32;
|
2004-10-05 18:51:11 +00:00
|
|
|
struct rusage ru, *rup;
|
2002-07-20 02:56:12 +00:00
|
|
|
|
2004-10-05 18:51:11 +00:00
|
|
|
if (uap->rusage != NULL)
|
|
|
|
rup = &ru;
|
|
|
|
else
|
|
|
|
rup = NULL;
|
|
|
|
error = kern_wait(td, uap->pid, &status, uap->options, rup);
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
2004-03-17 20:00:00 +00:00
|
|
|
if (uap->status != NULL)
|
|
|
|
error = copyout(&status, uap->status, sizeof(status));
|
|
|
|
if (uap->rusage != NULL && error == 0) {
|
2010-04-21 19:28:01 +00:00
|
|
|
freebsd32_rusage_out(&ru, &ru32);
|
2004-03-17 20:00:00 +00:00
|
|
|
error = copyout(&ru32, uap->rusage, sizeof(ru32));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2012-11-13 12:52:31 +00:00
|
|
|
int
|
|
|
|
freebsd32_wait6(struct thread *td, struct freebsd32_wait6_args *uap)
|
|
|
|
{
|
|
|
|
struct wrusage32 wru32;
|
|
|
|
struct __wrusage wru, *wrup;
|
|
|
|
struct siginfo32 si32;
|
|
|
|
struct __siginfo si, *sip;
|
|
|
|
int error, status;
|
|
|
|
|
|
|
|
if (uap->wrusage != NULL)
|
|
|
|
wrup = &wru;
|
|
|
|
else
|
|
|
|
wrup = NULL;
|
|
|
|
if (uap->info != NULL) {
|
|
|
|
sip = &si;
|
|
|
|
bzero(sip, sizeof(*sip));
|
|
|
|
} else
|
|
|
|
sip = NULL;
|
2013-05-21 11:40:16 +00:00
|
|
|
error = kern_wait6(td, uap->idtype, PAIR32TO64(id_t, uap->id),
|
|
|
|
&status, uap->options, wrup, sip);
|
2012-11-13 12:52:31 +00:00
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
if (uap->status != NULL)
|
|
|
|
error = copyout(&status, uap->status, sizeof(status));
|
|
|
|
if (uap->wrusage != NULL && error == 0) {
|
|
|
|
freebsd32_rusage_out(&wru.wru_self, &wru32.wru_self);
|
|
|
|
freebsd32_rusage_out(&wru.wru_children, &wru32.wru_children);
|
|
|
|
error = copyout(&wru32, uap->wrusage, sizeof(wru32));
|
|
|
|
}
|
|
|
|
if (uap->info != NULL && error == 0) {
|
|
|
|
siginfo_to_siginfo32 (&si, &si32);
|
|
|
|
error = copyout(&si32, uap->info, sizeof(si32));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2004-04-24 04:31:59 +00:00
|
|
|
#ifdef COMPAT_FREEBSD4
|
2007-12-10 19:42:23 +00:00
|
|
|
static void
|
2002-07-20 02:56:12 +00:00
|
|
|
copy_statfs(struct statfs *in, struct statfs32 *out)
|
|
|
|
{
|
2007-08-28 20:28:12 +00:00
|
|
|
|
2007-12-07 22:32:09 +00:00
|
|
|
statfs_scale_blocks(in, INT32_MAX);
|
2006-03-04 00:09:09 +00:00
|
|
|
bzero(out, sizeof(*out));
|
2002-07-20 02:56:12 +00:00
|
|
|
CP(*in, *out, f_bsize);
|
2007-08-28 20:28:12 +00:00
|
|
|
out->f_iosize = MIN(in->f_iosize, INT32_MAX);
|
2002-07-20 02:56:12 +00:00
|
|
|
CP(*in, *out, f_blocks);
|
|
|
|
CP(*in, *out, f_bfree);
|
|
|
|
CP(*in, *out, f_bavail);
|
2007-08-28 20:28:12 +00:00
|
|
|
out->f_files = MIN(in->f_files, INT32_MAX);
|
2007-12-10 19:42:23 +00:00
|
|
|
out->f_ffree = MIN(in->f_ffree, INT32_MAX);
|
2002-07-20 02:56:12 +00:00
|
|
|
CP(*in, *out, f_fsid);
|
|
|
|
CP(*in, *out, f_owner);
|
|
|
|
CP(*in, *out, f_type);
|
|
|
|
CP(*in, *out, f_flags);
|
2007-12-10 19:42:23 +00:00
|
|
|
out->f_syncwrites = MIN(in->f_syncwrites, INT32_MAX);
|
|
|
|
out->f_asyncwrites = MIN(in->f_asyncwrites, INT32_MAX);
|
2006-03-04 00:09:09 +00:00
|
|
|
strlcpy(out->f_fstypename,
|
|
|
|
in->f_fstypename, MFSNAMELEN);
|
|
|
|
strlcpy(out->f_mntonname,
|
|
|
|
in->f_mntonname, min(MNAMELEN, FREEBSD4_MNAMELEN));
|
2007-12-10 19:42:23 +00:00
|
|
|
out->f_syncreads = MIN(in->f_syncreads, INT32_MAX);
|
|
|
|
out->f_asyncreads = MIN(in->f_asyncreads, INT32_MAX);
|
2006-03-04 00:09:09 +00:00
|
|
|
strlcpy(out->f_mntfromname,
|
|
|
|
in->f_mntfromname, min(MNAMELEN, FREEBSD4_MNAMELEN));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
2004-04-24 04:31:59 +00:00
|
|
|
#endif
|
2002-07-20 02:56:12 +00:00
|
|
|
|
2004-04-24 04:31:59 +00:00
|
|
|
#ifdef COMPAT_FREEBSD4
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2017-01-05 17:03:35 +00:00
|
|
|
freebsd4_freebsd32_getfsstat(struct thread *td,
|
|
|
|
struct freebsd4_freebsd32_getfsstat_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2005-06-09 17:44:46 +00:00
|
|
|
struct statfs *buf, *sp;
|
|
|
|
struct statfs32 stat32;
|
2015-05-05 05:14:12 +00:00
|
|
|
size_t count, size, copycount;
|
2002-07-20 02:56:12 +00:00
|
|
|
int error;
|
|
|
|
|
2005-06-09 17:44:46 +00:00
|
|
|
count = uap->bufsize / sizeof(struct statfs32);
|
|
|
|
size = count * sizeof(struct statfs);
|
2016-12-27 20:21:11 +00:00
|
|
|
error = kern_getfsstat(td, &buf, size, &count, UIO_SYSSPACE, uap->mode);
|
2005-06-11 14:58:20 +00:00
|
|
|
if (size > 0) {
|
2005-06-09 17:44:46 +00:00
|
|
|
sp = buf;
|
2015-05-05 05:14:12 +00:00
|
|
|
copycount = count;
|
|
|
|
while (copycount > 0 && error == 0) {
|
2007-12-10 19:42:23 +00:00
|
|
|
copy_statfs(sp, &stat32);
|
2005-06-09 17:44:46 +00:00
|
|
|
error = copyout(&stat32, uap->buf, sizeof(stat32));
|
|
|
|
sp++;
|
|
|
|
uap->buf++;
|
2015-05-05 05:14:12 +00:00
|
|
|
copycount--;
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
2017-01-05 17:19:26 +00:00
|
|
|
free(buf, M_STATFS);
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
2015-04-15 09:13:11 +00:00
|
|
|
if (error == 0)
|
|
|
|
td->td_retval[0] = count;
|
2002-07-20 02:56:12 +00:00
|
|
|
return (error);
|
|
|
|
}
|
2004-04-24 04:31:59 +00:00
|
|
|
#endif
|
2002-07-20 02:56:12 +00:00
|
|
|
|
2016-06-22 21:18:19 +00:00
|
|
|
#ifdef COMPAT_FREEBSD10
|
|
|
|
int
|
|
|
|
freebsd10_freebsd32_pipe(struct thread *td,
|
|
|
|
struct freebsd10_freebsd32_pipe_args *uap) {
|
|
|
|
|
|
|
|
return (freebsd10_pipe(td, (struct freebsd10_pipe_args*)uap));
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_sigaltstack(struct thread *td,
|
|
|
|
struct freebsd32_sigaltstack_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2003-04-22 18:23:49 +00:00
|
|
|
struct sigaltstack32 s32;
|
|
|
|
struct sigaltstack ss, oss, *ssp;
|
2002-07-20 02:56:12 +00:00
|
|
|
int error;
|
|
|
|
|
2003-04-22 18:23:49 +00:00
|
|
|
if (uap->ss != NULL) {
|
|
|
|
error = copyin(uap->ss, &s32, sizeof(s32));
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
2003-04-22 18:23:49 +00:00
|
|
|
PTRIN_CP(s32, ss, ss_sp);
|
|
|
|
CP(s32, ss, ss_size);
|
|
|
|
CP(s32, ss, ss_flags);
|
|
|
|
ssp = &ss;
|
|
|
|
} else
|
|
|
|
ssp = NULL;
|
|
|
|
error = kern_sigaltstack(td, ssp, &oss);
|
|
|
|
if (error == 0 && uap->oss != NULL) {
|
|
|
|
PTROUT_CP(oss, s32, ss_sp);
|
|
|
|
CP(oss, s32, ss_size);
|
|
|
|
CP(oss, s32, ss_flags);
|
|
|
|
error = copyout(&s32, uap->oss, sizeof(s32));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
/*
|
|
|
|
* Custom version of exec_copyin_args() so that we can translate
|
|
|
|
* the pointers.
|
|
|
|
*/
|
2010-07-23 21:30:33 +00:00
|
|
|
int
|
2018-11-02 20:50:22 +00:00
|
|
|
freebsd32_exec_copyin_args(struct image_args *args, const char *fname,
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
enum uio_seg segflg, u_int32_t *argv, u_int32_t *envv)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
char *argp, *envp;
|
2002-07-20 02:56:12 +00:00
|
|
|
u_int32_t *p32, arg;
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
int error;
|
2002-07-20 02:56:12 +00:00
|
|
|
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
bzero(args, sizeof(*args));
|
|
|
|
if (argv == NULL)
|
|
|
|
return (EFAULT);
|
2002-07-20 02:56:12 +00:00
|
|
|
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
/*
|
2010-07-27 17:31:03 +00:00
|
|
|
* Allocate demand-paged memory for the file name, argument, and
|
|
|
|
* environment strings.
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
*/
|
2010-07-27 17:31:03 +00:00
|
|
|
error = exec_alloc_args(args);
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* Copy the file name.
|
|
|
|
*/
|
2018-11-29 21:00:56 +00:00
|
|
|
error = exec_args_add_fname(args, fname, segflg);
|
|
|
|
if (error != 0)
|
|
|
|
goto err_exit;
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* extract arguments first
|
|
|
|
*/
|
|
|
|
p32 = argv;
|
|
|
|
for (;;) {
|
|
|
|
error = copyin(p32++, &arg, sizeof(arg));
|
|
|
|
if (error)
|
2006-03-08 20:21:54 +00:00
|
|
|
goto err_exit;
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
if (arg == 0)
|
|
|
|
break;
|
|
|
|
argp = PTRIN(arg);
|
2018-11-29 21:00:56 +00:00
|
|
|
error = exec_args_add_arg(args, argp, UIO_USERSPACE);
|
|
|
|
if (error != 0)
|
2006-03-08 20:21:54 +00:00
|
|
|
goto err_exit;
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* extract environment strings
|
|
|
|
*/
|
|
|
|
if (envv) {
|
|
|
|
p32 = envv;
|
|
|
|
for (;;) {
|
2002-07-20 02:56:12 +00:00
|
|
|
error = copyin(p32++, &arg, sizeof(arg));
|
|
|
|
if (error)
|
2006-03-08 20:21:54 +00:00
|
|
|
goto err_exit;
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
if (arg == 0)
|
|
|
|
break;
|
|
|
|
envp = PTRIN(arg);
|
2018-11-29 21:00:56 +00:00
|
|
|
error = exec_args_add_env(args, envp, UIO_USERSPACE);
|
|
|
|
if (error != 0)
|
2006-03-08 20:21:54 +00:00
|
|
|
goto err_exit;
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
}
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
return (0);
|
2006-03-08 20:21:54 +00:00
|
|
|
|
|
|
|
err_exit:
|
2010-07-23 18:58:27 +00:00
|
|
|
exec_free_args(args);
|
2006-03-08 20:21:54 +00:00
|
|
|
return (error);
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_execve(struct thread *td, struct freebsd32_execve_args *uap)
|
|
|
|
{
|
|
|
|
struct image_args eargs;
|
2015-05-10 09:00:40 +00:00
|
|
|
struct vmspace *oldvmspace;
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
int error;
|
|
|
|
|
2015-05-10 09:00:40 +00:00
|
|
|
error = pre_execve(td, &oldvmspace);
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
error = freebsd32_exec_copyin_args(&eargs, uap->fname, UIO_USERSPACE,
|
|
|
|
uap->argv, uap->envv);
|
|
|
|
if (error == 0)
|
|
|
|
error = kern_execve(td, &eargs, NULL);
|
2015-05-10 09:00:40 +00:00
|
|
|
post_execve(td, error, oldvmspace);
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
return (error);
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
2008-03-31 12:08:30 +00:00
|
|
|
int
|
|
|
|
freebsd32_fexecve(struct thread *td, struct freebsd32_fexecve_args *uap)
|
|
|
|
{
|
|
|
|
struct image_args eargs;
|
2015-05-10 09:00:40 +00:00
|
|
|
struct vmspace *oldvmspace;
|
2008-03-31 12:08:30 +00:00
|
|
|
int error;
|
|
|
|
|
2015-05-10 09:00:40 +00:00
|
|
|
error = pre_execve(td, &oldvmspace);
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
2008-03-31 12:08:30 +00:00
|
|
|
error = freebsd32_exec_copyin_args(&eargs, NULL, UIO_SYSSPACE,
|
|
|
|
uap->argv, uap->envv);
|
|
|
|
if (error == 0) {
|
|
|
|
eargs.fd = uap->fd;
|
|
|
|
error = kern_execve(td, &eargs, NULL);
|
|
|
|
}
|
2015-05-10 09:00:40 +00:00
|
|
|
post_execve(td, error, oldvmspace);
|
2008-03-31 12:08:30 +00:00
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
|
|
|
|
int
|
2018-11-09 21:01:16 +00:00
|
|
|
freebsd32_mknodat(struct thread *td, struct freebsd32_mknodat_args *uap)
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
{
|
|
|
|
|
2018-11-09 21:01:16 +00:00
|
|
|
return (kern_mknodat(td, uap->fd, uap->path, UIO_USERSPACE,
|
|
|
|
uap->mode, PAIR32TO64(dev_t, uap->dev)));
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
}
|
|
|
|
|
2011-10-13 18:25:10 +00:00
|
|
|
int
|
|
|
|
freebsd32_mprotect(struct thread *td, struct freebsd32_mprotect_args *uap)
|
|
|
|
{
|
2017-02-06 20:57:12 +00:00
|
|
|
int prot;
|
2011-10-13 18:25:10 +00:00
|
|
|
|
2017-02-06 20:57:12 +00:00
|
|
|
prot = uap->prot;
|
2014-07-07 00:27:09 +00:00
|
|
|
#if defined(__amd64__)
|
2017-02-06 20:57:12 +00:00
|
|
|
if (i386_read_exec && (prot & PROT_READ) != 0)
|
|
|
|
prot |= PROT_EXEC;
|
2011-10-13 18:25:10 +00:00
|
|
|
#endif
|
2017-02-13 09:04:38 +00:00
|
|
|
return (kern_mprotect(td, (uintptr_t)PTRIN(uap->addr), uap->len,
|
|
|
|
prot));
|
2011-10-13 18:25:10 +00:00
|
|
|
}
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_mmap(struct thread *td, struct freebsd32_mmap_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2017-02-06 20:57:12 +00:00
|
|
|
int prot;
|
2002-07-20 02:56:12 +00:00
|
|
|
|
2017-02-06 20:57:12 +00:00
|
|
|
prot = uap->prot;
|
2014-07-07 00:27:09 +00:00
|
|
|
#if defined(__amd64__)
|
2011-10-15 12:35:18 +00:00
|
|
|
if (i386_read_exec && (prot & PROT_READ))
|
2011-10-13 18:18:42 +00:00
|
|
|
prot |= PROT_EXEC;
|
|
|
|
#endif
|
|
|
|
|
2017-02-13 09:04:38 +00:00
|
|
|
return (kern_mmap(td, (uintptr_t)uap->addr, uap->len, prot,
|
2017-02-06 20:57:12 +00:00
|
|
|
uap->flags, uap->fd, PAIR32TO64(off_t, uap->pos)));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
2007-07-04 23:04:41 +00:00
|
|
|
#ifdef COMPAT_FREEBSD6
|
|
|
|
int
|
2017-02-13 00:39:43 +00:00
|
|
|
freebsd6_freebsd32_mmap(struct thread *td,
|
|
|
|
struct freebsd6_freebsd32_mmap_args *uap)
|
2007-07-04 23:04:41 +00:00
|
|
|
{
|
2017-02-13 09:04:38 +00:00
|
|
|
int prot;
|
2007-07-04 23:04:41 +00:00
|
|
|
|
2017-02-13 09:04:38 +00:00
|
|
|
prot = uap->prot;
|
|
|
|
#if defined(__amd64__)
|
|
|
|
if (i386_read_exec && (prot & PROT_READ))
|
|
|
|
prot |= PROT_EXEC;
|
|
|
|
#endif
|
2007-07-04 23:04:41 +00:00
|
|
|
|
2017-02-13 09:04:38 +00:00
|
|
|
return (kern_mmap(td, (uintptr_t)uap->addr, uap->len, prot,
|
|
|
|
uap->flags, uap->fd, PAIR32TO64(off_t, uap->pos)));
|
2007-07-04 23:04:41 +00:00
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_setitimer(struct thread *td, struct freebsd32_setitimer_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
struct itimerval itv, oitv, *itvp;
|
|
|
|
struct itimerval32 i32;
|
2002-07-20 02:56:12 +00:00
|
|
|
int error;
|
|
|
|
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
if (uap->itv != NULL) {
|
|
|
|
error = copyin(uap->itv, &i32, sizeof(i32));
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
TV_CP(i32, itv, it_interval);
|
|
|
|
TV_CP(i32, itv, it_value);
|
|
|
|
itvp = &itv;
|
|
|
|
} else
|
|
|
|
itvp = NULL;
|
|
|
|
error = kern_setitimer(td, uap->which, itvp, &oitv);
|
|
|
|
if (error || uap->oitv == NULL)
|
2002-07-20 02:56:12 +00:00
|
|
|
return (error);
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
TV_CP(oitv, i32, it_interval);
|
|
|
|
TV_CP(oitv, i32, it_value);
|
|
|
|
return (copyout(&i32, uap->oitv, sizeof(i32)));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
2004-01-28 23:45:48 +00:00
|
|
|
int
|
|
|
|
freebsd32_getitimer(struct thread *td, struct freebsd32_getitimer_args *uap)
|
|
|
|
{
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
struct itimerval itv;
|
|
|
|
struct itimerval32 i32;
|
2004-01-28 23:45:48 +00:00
|
|
|
int error;
|
|
|
|
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
error = kern_getitimer(td, uap->which, &itv);
|
|
|
|
if (error || uap->itv == NULL)
|
2004-01-28 23:45:48 +00:00
|
|
|
return (error);
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
TV_CP(itv, i32, it_interval);
|
|
|
|
TV_CP(itv, i32, it_value);
|
|
|
|
return (copyout(&i32, uap->itv, sizeof(i32)));
|
2004-01-28 23:45:48 +00:00
|
|
|
}
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_select(struct thread *td, struct freebsd32_select_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
struct timeval32 tv32;
|
|
|
|
struct timeval tv, *tvp;
|
2002-07-20 02:56:12 +00:00
|
|
|
int error;
|
|
|
|
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
if (uap->tv != NULL) {
|
|
|
|
error = copyin(uap->tv, &tv32, sizeof(tv32));
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
CP(tv32, tv, tv_sec);
|
|
|
|
CP(tv32, tv, tv_usec);
|
|
|
|
tvp = &tv;
|
|
|
|
} else
|
|
|
|
tvp = NULL;
|
2002-07-20 02:56:12 +00:00
|
|
|
/*
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
* XXX Do pointers need PTRIN()?
|
2002-07-20 02:56:12 +00:00
|
|
|
*/
|
2009-09-09 20:59:01 +00:00
|
|
|
return (kern_select(td, uap->nd, uap->in, uap->ou, uap->ex, tvp,
|
|
|
|
sizeof(int32_t) * 8));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
2009-10-27 10:55:34 +00:00
|
|
|
int
|
|
|
|
freebsd32_pselect(struct thread *td, struct freebsd32_pselect_args *uap)
|
|
|
|
{
|
|
|
|
struct timespec32 ts32;
|
|
|
|
struct timespec ts;
|
|
|
|
struct timeval tv, *tvp;
|
|
|
|
sigset_t set, *uset;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->ts != NULL) {
|
|
|
|
error = copyin(uap->ts, &ts32, sizeof(ts32));
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
CP(ts32, ts, tv_sec);
|
|
|
|
CP(ts32, ts, tv_nsec);
|
|
|
|
TIMESPEC_TO_TIMEVAL(&tv, &ts);
|
|
|
|
tvp = &tv;
|
|
|
|
} else
|
|
|
|
tvp = NULL;
|
|
|
|
if (uap->sm != NULL) {
|
|
|
|
error = copyin(uap->sm, &set, sizeof(set));
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
uset = &set;
|
|
|
|
} else
|
|
|
|
uset = NULL;
|
|
|
|
/*
|
|
|
|
* XXX Do pointers need PTRIN()?
|
|
|
|
*/
|
|
|
|
error = kern_pselect(td, uap->nd, uap->in, uap->ou, uap->ex, tvp,
|
|
|
|
uset, sizeof(int32_t) * 8);
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2005-06-03 23:15:01 +00:00
|
|
|
/*
|
|
|
|
* Copy 'count' items into the destination list pointed to by uap->eventlist.
|
|
|
|
*/
|
|
|
|
static int
|
|
|
|
freebsd32_kevent_copyout(void *arg, struct kevent *kevp, int count)
|
|
|
|
{
|
|
|
|
struct freebsd32_kevent_args *uap;
|
|
|
|
struct kevent32 ks32[KQ_NEVENTS];
|
Add abstime kqueue(2) timers and expand struct kevent members.
This change implements NOTE_ABSTIME flag for EVFILT_TIMER, which
specifies that the data field contains absolute time to fire the
event.
To make this useful, data member of the struct kevent must be extended
to 64bit. Using the opportunity, I also added ext members. This
changes struct kevent almost to Apple struct kevent64, except I did
not changed type of ident and udata, the later would cause serious API
incompatibilities.
The type of ident was kept uintptr_t since EVFILT_AIO returns a
pointer in this field, and e.g. CHERI is sensitive to the type
(discussed with brooks, jhb).
Unlike Apple kevent64, symbol versioning allows us to claim ABI
compatibility and still name the new syscall kevent(2). Compat shims
are provided for both host native and compat32.
Requested by: bapt
Reviewed by: bapt, brooks, ngie (previous version)
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D11025
2017-06-17 00:57:26 +00:00
|
|
|
uint64_t e;
|
|
|
|
int i, j, error;
|
2005-06-03 23:15:01 +00:00
|
|
|
|
|
|
|
KASSERT(count <= KQ_NEVENTS, ("count (%d) > KQ_NEVENTS", count));
|
|
|
|
uap = (struct freebsd32_kevent_args *)arg;
|
|
|
|
|
|
|
|
for (i = 0; i < count; i++) {
|
|
|
|
CP(kevp[i], ks32[i], ident);
|
|
|
|
CP(kevp[i], ks32[i], filter);
|
|
|
|
CP(kevp[i], ks32[i], flags);
|
|
|
|
CP(kevp[i], ks32[i], fflags);
|
Add abstime kqueue(2) timers and expand struct kevent members.
This change implements NOTE_ABSTIME flag for EVFILT_TIMER, which
specifies that the data field contains absolute time to fire the
event.
To make this useful, data member of the struct kevent must be extended
to 64bit. Using the opportunity, I also added ext members. This
changes struct kevent almost to Apple struct kevent64, except I did
not changed type of ident and udata, the later would cause serious API
incompatibilities.
The type of ident was kept uintptr_t since EVFILT_AIO returns a
pointer in this field, and e.g. CHERI is sensitive to the type
(discussed with brooks, jhb).
Unlike Apple kevent64, symbol versioning allows us to claim ABI
compatibility and still name the new syscall kevent(2). Compat shims
are provided for both host native and compat32.
Requested by: bapt
Reviewed by: bapt, brooks, ngie (previous version)
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D11025
2017-06-17 00:57:26 +00:00
|
|
|
#if BYTE_ORDER == LITTLE_ENDIAN
|
|
|
|
ks32[i].data1 = kevp[i].data;
|
|
|
|
ks32[i].data2 = kevp[i].data >> 32;
|
|
|
|
#else
|
|
|
|
ks32[i].data1 = kevp[i].data >> 32;
|
|
|
|
ks32[i].data2 = kevp[i].data;
|
|
|
|
#endif
|
2005-06-03 23:15:01 +00:00
|
|
|
PTROUT_CP(kevp[i], ks32[i], udata);
|
Add abstime kqueue(2) timers and expand struct kevent members.
This change implements NOTE_ABSTIME flag for EVFILT_TIMER, which
specifies that the data field contains absolute time to fire the
event.
To make this useful, data member of the struct kevent must be extended
to 64bit. Using the opportunity, I also added ext members. This
changes struct kevent almost to Apple struct kevent64, except I did
not changed type of ident and udata, the later would cause serious API
incompatibilities.
The type of ident was kept uintptr_t since EVFILT_AIO returns a
pointer in this field, and e.g. CHERI is sensitive to the type
(discussed with brooks, jhb).
Unlike Apple kevent64, symbol versioning allows us to claim ABI
compatibility and still name the new syscall kevent(2). Compat shims
are provided for both host native and compat32.
Requested by: bapt
Reviewed by: bapt, brooks, ngie (previous version)
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D11025
2017-06-17 00:57:26 +00:00
|
|
|
for (j = 0; j < nitems(kevp->ext); j++) {
|
|
|
|
e = kevp[i].ext[j];
|
|
|
|
#if BYTE_ORDER == LITTLE_ENDIAN
|
|
|
|
ks32[i].ext64[2 * j] = e;
|
|
|
|
ks32[i].ext64[2 * j + 1] = e >> 32;
|
|
|
|
#else
|
|
|
|
ks32[i].ext64[2 * j] = e >> 32;
|
|
|
|
ks32[i].ext64[2 * j + 1] = e;
|
|
|
|
#endif
|
|
|
|
}
|
2005-06-03 23:15:01 +00:00
|
|
|
}
|
|
|
|
error = copyout(ks32, uap->eventlist, count * sizeof *ks32);
|
|
|
|
if (error == 0)
|
|
|
|
uap->eventlist += count;
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Copy 'count' items from the list pointed to by uap->changelist.
|
|
|
|
*/
|
|
|
|
static int
|
|
|
|
freebsd32_kevent_copyin(void *arg, struct kevent *kevp, int count)
|
|
|
|
{
|
|
|
|
struct freebsd32_kevent_args *uap;
|
|
|
|
struct kevent32 ks32[KQ_NEVENTS];
|
Add abstime kqueue(2) timers and expand struct kevent members.
This change implements NOTE_ABSTIME flag for EVFILT_TIMER, which
specifies that the data field contains absolute time to fire the
event.
To make this useful, data member of the struct kevent must be extended
to 64bit. Using the opportunity, I also added ext members. This
changes struct kevent almost to Apple struct kevent64, except I did
not changed type of ident and udata, the later would cause serious API
incompatibilities.
The type of ident was kept uintptr_t since EVFILT_AIO returns a
pointer in this field, and e.g. CHERI is sensitive to the type
(discussed with brooks, jhb).
Unlike Apple kevent64, symbol versioning allows us to claim ABI
compatibility and still name the new syscall kevent(2). Compat shims
are provided for both host native and compat32.
Requested by: bapt
Reviewed by: bapt, brooks, ngie (previous version)
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D11025
2017-06-17 00:57:26 +00:00
|
|
|
uint64_t e;
|
|
|
|
int i, j, error;
|
2005-06-03 23:15:01 +00:00
|
|
|
|
|
|
|
KASSERT(count <= KQ_NEVENTS, ("count (%d) > KQ_NEVENTS", count));
|
|
|
|
uap = (struct freebsd32_kevent_args *)arg;
|
|
|
|
|
|
|
|
error = copyin(uap->changelist, ks32, count * sizeof *ks32);
|
|
|
|
if (error)
|
|
|
|
goto done;
|
|
|
|
uap->changelist += count;
|
|
|
|
|
|
|
|
for (i = 0; i < count; i++) {
|
|
|
|
CP(ks32[i], kevp[i], ident);
|
|
|
|
CP(ks32[i], kevp[i], filter);
|
|
|
|
CP(ks32[i], kevp[i], flags);
|
|
|
|
CP(ks32[i], kevp[i], fflags);
|
Add abstime kqueue(2) timers and expand struct kevent members.
This change implements NOTE_ABSTIME flag for EVFILT_TIMER, which
specifies that the data field contains absolute time to fire the
event.
To make this useful, data member of the struct kevent must be extended
to 64bit. Using the opportunity, I also added ext members. This
changes struct kevent almost to Apple struct kevent64, except I did
not changed type of ident and udata, the later would cause serious API
incompatibilities.
The type of ident was kept uintptr_t since EVFILT_AIO returns a
pointer in this field, and e.g. CHERI is sensitive to the type
(discussed with brooks, jhb).
Unlike Apple kevent64, symbol versioning allows us to claim ABI
compatibility and still name the new syscall kevent(2). Compat shims
are provided for both host native and compat32.
Requested by: bapt
Reviewed by: bapt, brooks, ngie (previous version)
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D11025
2017-06-17 00:57:26 +00:00
|
|
|
kevp[i].data = PAIR32TO64(uint64_t, ks32[i].data);
|
2005-06-03 23:15:01 +00:00
|
|
|
PTRIN_CP(ks32[i], kevp[i], udata);
|
Add abstime kqueue(2) timers and expand struct kevent members.
This change implements NOTE_ABSTIME flag for EVFILT_TIMER, which
specifies that the data field contains absolute time to fire the
event.
To make this useful, data member of the struct kevent must be extended
to 64bit. Using the opportunity, I also added ext members. This
changes struct kevent almost to Apple struct kevent64, except I did
not changed type of ident and udata, the later would cause serious API
incompatibilities.
The type of ident was kept uintptr_t since EVFILT_AIO returns a
pointer in this field, and e.g. CHERI is sensitive to the type
(discussed with brooks, jhb).
Unlike Apple kevent64, symbol versioning allows us to claim ABI
compatibility and still name the new syscall kevent(2). Compat shims
are provided for both host native and compat32.
Requested by: bapt
Reviewed by: bapt, brooks, ngie (previous version)
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D11025
2017-06-17 00:57:26 +00:00
|
|
|
for (j = 0; j < nitems(kevp->ext); j++) {
|
|
|
|
#if BYTE_ORDER == LITTLE_ENDIAN
|
|
|
|
e = ks32[i].ext64[2 * j + 1];
|
|
|
|
e <<= 32;
|
|
|
|
e += ks32[i].ext64[2 * j];
|
|
|
|
#else
|
|
|
|
e = ks32[i].ext64[2 * j];
|
|
|
|
e <<= 32;
|
|
|
|
e += ks32[i].ext64[2 * j + 1];
|
|
|
|
#endif
|
|
|
|
kevp[i].ext[j] = e;
|
|
|
|
}
|
2005-06-03 23:15:01 +00:00
|
|
|
}
|
|
|
|
done:
|
|
|
|
return (error);
|
|
|
|
}
|
2003-10-30 02:40:30 +00:00
|
|
|
|
2003-05-14 04:10:49 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_kevent(struct thread *td, struct freebsd32_kevent_args *uap)
|
2003-05-14 04:10:49 +00:00
|
|
|
{
|
|
|
|
struct timespec32 ts32;
|
2005-03-01 17:45:55 +00:00
|
|
|
struct timespec ts, *tsp;
|
2017-03-14 09:25:01 +00:00
|
|
|
struct kevent_copyops k_ops = {
|
|
|
|
.arg = uap,
|
|
|
|
.k_copyout = freebsd32_kevent_copyout,
|
|
|
|
.k_copyin = freebsd32_kevent_copyin,
|
|
|
|
};
|
2017-11-25 04:49:12 +00:00
|
|
|
#ifdef KTRACE
|
|
|
|
struct kevent32 *eventlist = uap->eventlist;
|
|
|
|
#endif
|
2005-06-03 23:15:01 +00:00
|
|
|
int error;
|
2003-05-14 04:10:49 +00:00
|
|
|
|
Add abstime kqueue(2) timers and expand struct kevent members.
This change implements NOTE_ABSTIME flag for EVFILT_TIMER, which
specifies that the data field contains absolute time to fire the
event.
To make this useful, data member of the struct kevent must be extended
to 64bit. Using the opportunity, I also added ext members. This
changes struct kevent almost to Apple struct kevent64, except I did
not changed type of ident and udata, the later would cause serious API
incompatibilities.
The type of ident was kept uintptr_t since EVFILT_AIO returns a
pointer in this field, and e.g. CHERI is sensitive to the type
(discussed with brooks, jhb).
Unlike Apple kevent64, symbol versioning allows us to claim ABI
compatibility and still name the new syscall kevent(2). Compat shims
are provided for both host native and compat32.
Requested by: bapt
Reviewed by: bapt, brooks, ngie (previous version)
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D11025
2017-06-17 00:57:26 +00:00
|
|
|
if (uap->timeout) {
|
|
|
|
error = copyin(uap->timeout, &ts32, sizeof(ts32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
CP(ts32, ts, tv_sec);
|
|
|
|
CP(ts32, ts, tv_nsec);
|
|
|
|
tsp = &ts;
|
|
|
|
} else
|
|
|
|
tsp = NULL;
|
2017-11-25 04:49:12 +00:00
|
|
|
#ifdef KTRACE
|
|
|
|
if (KTRPOINT(td, KTR_STRUCT_ARRAY))
|
|
|
|
ktrstructarray("kevent32", UIO_USERSPACE, uap->changelist,
|
|
|
|
uap->nchanges, sizeof(struct kevent32));
|
|
|
|
#endif
|
Add abstime kqueue(2) timers and expand struct kevent members.
This change implements NOTE_ABSTIME flag for EVFILT_TIMER, which
specifies that the data field contains absolute time to fire the
event.
To make this useful, data member of the struct kevent must be extended
to 64bit. Using the opportunity, I also added ext members. This
changes struct kevent almost to Apple struct kevent64, except I did
not changed type of ident and udata, the later would cause serious API
incompatibilities.
The type of ident was kept uintptr_t since EVFILT_AIO returns a
pointer in this field, and e.g. CHERI is sensitive to the type
(discussed with brooks, jhb).
Unlike Apple kevent64, symbol versioning allows us to claim ABI
compatibility and still name the new syscall kevent(2). Compat shims
are provided for both host native and compat32.
Requested by: bapt
Reviewed by: bapt, brooks, ngie (previous version)
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D11025
2017-06-17 00:57:26 +00:00
|
|
|
error = kern_kevent(td, uap->fd, uap->nchanges, uap->nevents,
|
|
|
|
&k_ops, tsp);
|
2017-11-25 04:49:12 +00:00
|
|
|
#ifdef KTRACE
|
|
|
|
if (error == 0 && KTRPOINT(td, KTR_STRUCT_ARRAY))
|
|
|
|
ktrstructarray("kevent32", UIO_USERSPACE, eventlist,
|
|
|
|
td->td_retval[0], sizeof(struct kevent32));
|
|
|
|
#endif
|
Add abstime kqueue(2) timers and expand struct kevent members.
This change implements NOTE_ABSTIME flag for EVFILT_TIMER, which
specifies that the data field contains absolute time to fire the
event.
To make this useful, data member of the struct kevent must be extended
to 64bit. Using the opportunity, I also added ext members. This
changes struct kevent almost to Apple struct kevent64, except I did
not changed type of ident and udata, the later would cause serious API
incompatibilities.
The type of ident was kept uintptr_t since EVFILT_AIO returns a
pointer in this field, and e.g. CHERI is sensitive to the type
(discussed with brooks, jhb).
Unlike Apple kevent64, symbol versioning allows us to claim ABI
compatibility and still name the new syscall kevent(2). Compat shims
are provided for both host native and compat32.
Requested by: bapt
Reviewed by: bapt, brooks, ngie (previous version)
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D11025
2017-06-17 00:57:26 +00:00
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
#ifdef COMPAT_FREEBSD11
|
|
|
|
static int
|
|
|
|
freebsd32_kevent11_copyout(void *arg, struct kevent *kevp, int count)
|
|
|
|
{
|
|
|
|
struct freebsd11_freebsd32_kevent_args *uap;
|
|
|
|
struct kevent32_freebsd11 ks32[KQ_NEVENTS];
|
|
|
|
int i, error;
|
|
|
|
|
|
|
|
KASSERT(count <= KQ_NEVENTS, ("count (%d) > KQ_NEVENTS", count));
|
|
|
|
uap = (struct freebsd11_freebsd32_kevent_args *)arg;
|
|
|
|
|
|
|
|
for (i = 0; i < count; i++) {
|
|
|
|
CP(kevp[i], ks32[i], ident);
|
|
|
|
CP(kevp[i], ks32[i], filter);
|
|
|
|
CP(kevp[i], ks32[i], flags);
|
|
|
|
CP(kevp[i], ks32[i], fflags);
|
|
|
|
CP(kevp[i], ks32[i], data);
|
|
|
|
PTROUT_CP(kevp[i], ks32[i], udata);
|
|
|
|
}
|
|
|
|
error = copyout(ks32, uap->eventlist, count * sizeof *ks32);
|
|
|
|
if (error == 0)
|
|
|
|
uap->eventlist += count;
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Copy 'count' items from the list pointed to by uap->changelist.
|
|
|
|
*/
|
|
|
|
static int
|
|
|
|
freebsd32_kevent11_copyin(void *arg, struct kevent *kevp, int count)
|
|
|
|
{
|
|
|
|
struct freebsd11_freebsd32_kevent_args *uap;
|
|
|
|
struct kevent32_freebsd11 ks32[KQ_NEVENTS];
|
|
|
|
int i, j, error;
|
|
|
|
|
|
|
|
KASSERT(count <= KQ_NEVENTS, ("count (%d) > KQ_NEVENTS", count));
|
|
|
|
uap = (struct freebsd11_freebsd32_kevent_args *)arg;
|
|
|
|
|
|
|
|
error = copyin(uap->changelist, ks32, count * sizeof *ks32);
|
|
|
|
if (error)
|
|
|
|
goto done;
|
|
|
|
uap->changelist += count;
|
|
|
|
|
|
|
|
for (i = 0; i < count; i++) {
|
|
|
|
CP(ks32[i], kevp[i], ident);
|
|
|
|
CP(ks32[i], kevp[i], filter);
|
|
|
|
CP(ks32[i], kevp[i], flags);
|
|
|
|
CP(ks32[i], kevp[i], fflags);
|
|
|
|
CP(ks32[i], kevp[i], data);
|
|
|
|
PTRIN_CP(ks32[i], kevp[i], udata);
|
|
|
|
for (j = 0; j < nitems(kevp->ext); j++)
|
|
|
|
kevp[i].ext[j] = 0;
|
|
|
|
}
|
|
|
|
done:
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd11_freebsd32_kevent(struct thread *td,
|
|
|
|
struct freebsd11_freebsd32_kevent_args *uap)
|
|
|
|
{
|
|
|
|
struct timespec32 ts32;
|
|
|
|
struct timespec ts, *tsp;
|
|
|
|
struct kevent_copyops k_ops = {
|
|
|
|
.arg = uap,
|
|
|
|
.k_copyout = freebsd32_kevent11_copyout,
|
|
|
|
.k_copyin = freebsd32_kevent11_copyin,
|
|
|
|
};
|
2017-11-25 04:49:12 +00:00
|
|
|
#ifdef KTRACE
|
|
|
|
struct kevent32_freebsd11 *eventlist = uap->eventlist;
|
|
|
|
#endif
|
Add abstime kqueue(2) timers and expand struct kevent members.
This change implements NOTE_ABSTIME flag for EVFILT_TIMER, which
specifies that the data field contains absolute time to fire the
event.
To make this useful, data member of the struct kevent must be extended
to 64bit. Using the opportunity, I also added ext members. This
changes struct kevent almost to Apple struct kevent64, except I did
not changed type of ident and udata, the later would cause serious API
incompatibilities.
The type of ident was kept uintptr_t since EVFILT_AIO returns a
pointer in this field, and e.g. CHERI is sensitive to the type
(discussed with brooks, jhb).
Unlike Apple kevent64, symbol versioning allows us to claim ABI
compatibility and still name the new syscall kevent(2). Compat shims
are provided for both host native and compat32.
Requested by: bapt
Reviewed by: bapt, brooks, ngie (previous version)
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D11025
2017-06-17 00:57:26 +00:00
|
|
|
int error;
|
2003-05-14 04:10:49 +00:00
|
|
|
|
|
|
|
if (uap->timeout) {
|
|
|
|
error = copyin(uap->timeout, &ts32, sizeof(ts32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
CP(ts32, ts, tv_sec);
|
|
|
|
CP(ts32, ts, tv_nsec);
|
2005-03-01 17:45:55 +00:00
|
|
|
tsp = &ts;
|
|
|
|
} else
|
|
|
|
tsp = NULL;
|
2017-11-25 04:49:12 +00:00
|
|
|
#ifdef KTRACE
|
|
|
|
if (KTRPOINT(td, KTR_STRUCT_ARRAY))
|
|
|
|
ktrstructarray("kevent32_freebsd11", UIO_USERSPACE,
|
|
|
|
uap->changelist, uap->nchanges,
|
|
|
|
sizeof(struct kevent32_freebsd11));
|
|
|
|
#endif
|
2005-06-03 23:15:01 +00:00
|
|
|
error = kern_kevent(td, uap->fd, uap->nchanges, uap->nevents,
|
|
|
|
&k_ops, tsp);
|
2017-11-25 04:49:12 +00:00
|
|
|
#ifdef KTRACE
|
|
|
|
if (error == 0 && KTRPOINT(td, KTR_STRUCT_ARRAY))
|
|
|
|
ktrstructarray("kevent32_freebsd11", UIO_USERSPACE,
|
|
|
|
eventlist, td->td_retval[0],
|
|
|
|
sizeof(struct kevent32_freebsd11));
|
|
|
|
#endif
|
2005-03-01 17:45:55 +00:00
|
|
|
return (error);
|
2003-05-14 04:10:49 +00:00
|
|
|
}
|
Add abstime kqueue(2) timers and expand struct kevent members.
This change implements NOTE_ABSTIME flag for EVFILT_TIMER, which
specifies that the data field contains absolute time to fire the
event.
To make this useful, data member of the struct kevent must be extended
to 64bit. Using the opportunity, I also added ext members. This
changes struct kevent almost to Apple struct kevent64, except I did
not changed type of ident and udata, the later would cause serious API
incompatibilities.
The type of ident was kept uintptr_t since EVFILT_AIO returns a
pointer in this field, and e.g. CHERI is sensitive to the type
(discussed with brooks, jhb).
Unlike Apple kevent64, symbol versioning allows us to claim ABI
compatibility and still name the new syscall kevent(2). Compat shims
are provided for both host native and compat32.
Requested by: bapt
Reviewed by: bapt, brooks, ngie (previous version)
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D11025
2017-06-17 00:57:26 +00:00
|
|
|
#endif
|
2003-05-14 04:10:49 +00:00
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_gettimeofday(struct thread *td,
|
|
|
|
struct freebsd32_gettimeofday_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2003-12-11 02:34:49 +00:00
|
|
|
struct timeval atv;
|
|
|
|
struct timeval32 atv32;
|
|
|
|
struct timezone rtz;
|
|
|
|
int error = 0;
|
|
|
|
|
|
|
|
if (uap->tp) {
|
|
|
|
microtime(&atv);
|
|
|
|
CP(atv, atv32, tv_sec);
|
|
|
|
CP(atv, atv32, tv_usec);
|
|
|
|
error = copyout(&atv32, uap->tp, sizeof (atv32));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
2003-12-11 02:34:49 +00:00
|
|
|
if (error == 0 && uap->tzp != NULL) {
|
Kill tz_minuteswest and tz_dsttime.
Research Unix, 7th Edition introduced TIMEZONE and DSTFLAG
compile-time constants in sys/param.h to communicate these values for
the machine. 4.2BSD moved from the compile-time to run-time and
introduced these variables and used for localtime() to return the
right offset from UTC (sometimes referred to as GMT, for this purpose
is the same). 4.4BSD migrated to using the tzdata code/database and
these variables were basically unused.
FreeBSD removed the real need for these with adjkerntz in
1995. However, some RTC clocks continued to use these variables,
though they were largely unused otherwise. Later, phk centeralized
most of the uses in utc_offset, but left it using both tz_minuteswest
and adjkerntz.
POSIX (IEEE Std 1003.1-2017) states in the gettimeofday specification
"If tzp is not a null pointer, the behavior is unspecified" so there's
no standards reason to retain it anymore. In fact, gettimeofday has
been marked as obsolecent, meaning it could be removed from a future
release of the standard. It is the only interface defined in POSIX
that references these two values. All other references come from the
tzdata database via tzset().
These were used to more faithfully implement early unix ABIs which
have been removed from FreeBSD. NetBSD has completely eliminated
these variables years ago. Linux has migrated to tzdata as well,
though these variables technically still exist for compatibility
with unspecified older programs.
So, there's no real reason to have them these days. They are a
historical vestige that's no longer used in any meaningful way.
Reviewed By: jhb@, brooks@
Differential Revision: https://reviews.freebsd.org/D19550
2019-03-12 04:49:47 +00:00
|
|
|
rtz.tz_minuteswest = 0;
|
|
|
|
rtz.tz_dsttime = 0;
|
2003-12-11 02:34:49 +00:00
|
|
|
error = copyout(&rtz, uap->tzp, sizeof (rtz));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_getrusage(struct thread *td, struct freebsd32_getrusage_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2004-10-05 18:51:11 +00:00
|
|
|
struct rusage32 s32;
|
|
|
|
struct rusage s;
|
2002-07-20 02:56:12 +00:00
|
|
|
int error;
|
|
|
|
|
2004-10-05 18:51:11 +00:00
|
|
|
error = kern_getrusage(td, uap->who, &s);
|
2018-07-29 19:20:13 +00:00
|
|
|
if (error == 0) {
|
|
|
|
freebsd32_rusage_out(&s, &s32);
|
2004-10-05 18:51:11 +00:00
|
|
|
error = copyout(&s32, uap->rusage, sizeof(s32));
|
2018-07-29 19:20:13 +00:00
|
|
|
}
|
2002-07-20 02:56:12 +00:00
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2005-03-31 22:58:13 +00:00
|
|
|
static int
|
|
|
|
freebsd32_copyinuio(struct iovec32 *iovp, u_int iovcnt, struct uio **uiop)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2005-03-31 22:58:13 +00:00
|
|
|
struct iovec32 iov32;
|
|
|
|
struct iovec *iov;
|
|
|
|
struct uio *uio;
|
|
|
|
u_int iovlen;
|
|
|
|
int error, i;
|
2002-07-20 02:56:12 +00:00
|
|
|
|
2005-03-31 22:58:13 +00:00
|
|
|
*uiop = NULL;
|
|
|
|
if (iovcnt > UIO_MAXIOV)
|
2002-07-20 02:56:12 +00:00
|
|
|
return (EINVAL);
|
2005-03-31 22:58:13 +00:00
|
|
|
iovlen = iovcnt * sizeof(struct iovec);
|
|
|
|
uio = malloc(iovlen + sizeof *uio, M_IOV, M_WAITOK);
|
|
|
|
iov = (struct iovec *)(uio + 1);
|
|
|
|
for (i = 0; i < iovcnt; i++) {
|
|
|
|
error = copyin(&iovp[i], &iov32, sizeof(struct iovec32));
|
|
|
|
if (error) {
|
|
|
|
free(uio, M_IOV);
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
iov[i].iov_base = PTRIN(iov32.iov_base);
|
|
|
|
iov[i].iov_len = iov32.iov_len;
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
2005-03-31 22:58:13 +00:00
|
|
|
uio->uio_iov = iov;
|
|
|
|
uio->uio_iovcnt = iovcnt;
|
|
|
|
uio->uio_segflg = UIO_USERSPACE;
|
|
|
|
uio->uio_offset = -1;
|
|
|
|
uio->uio_resid = 0;
|
|
|
|
for (i = 0; i < iovcnt; i++) {
|
|
|
|
if (iov->iov_len > INT_MAX - uio->uio_resid) {
|
|
|
|
free(uio, M_IOV);
|
|
|
|
return (EINVAL);
|
|
|
|
}
|
|
|
|
uio->uio_resid += iov->iov_len;
|
|
|
|
iov++;
|
|
|
|
}
|
|
|
|
*uiop = uio;
|
|
|
|
return (0);
|
|
|
|
}
|
2002-07-20 02:56:12 +00:00
|
|
|
|
2005-03-31 22:58:13 +00:00
|
|
|
int
|
|
|
|
freebsd32_readv(struct thread *td, struct freebsd32_readv_args *uap)
|
|
|
|
{
|
|
|
|
struct uio *auio;
|
|
|
|
int error;
|
2002-07-20 02:56:12 +00:00
|
|
|
|
2005-03-31 22:58:13 +00:00
|
|
|
error = freebsd32_copyinuio(uap->iovp, uap->iovcnt, &auio);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
error = kern_readv(td, uap->fd, auio);
|
|
|
|
free(auio, M_IOV);
|
2002-07-20 02:56:12 +00:00
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_writev(struct thread *td, struct freebsd32_writev_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2005-03-31 22:58:13 +00:00
|
|
|
struct uio *auio;
|
|
|
|
int error;
|
2002-07-20 02:56:12 +00:00
|
|
|
|
2005-03-31 22:58:13 +00:00
|
|
|
error = freebsd32_copyinuio(uap->iovp, uap->iovcnt, &auio);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
error = kern_writev(td, uap->fd, auio);
|
|
|
|
free(auio, M_IOV);
|
2002-07-20 02:56:12 +00:00
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2005-07-07 18:17:55 +00:00
|
|
|
int
|
|
|
|
freebsd32_preadv(struct thread *td, struct freebsd32_preadv_args *uap)
|
|
|
|
{
|
|
|
|
struct uio *auio;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = freebsd32_copyinuio(uap->iovp, uap->iovcnt, &auio);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
2010-03-11 14:49:06 +00:00
|
|
|
error = kern_preadv(td, uap->fd, auio, PAIR32TO64(off_t,uap->offset));
|
2005-07-07 18:17:55 +00:00
|
|
|
free(auio, M_IOV);
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_pwritev(struct thread *td, struct freebsd32_pwritev_args *uap)
|
|
|
|
{
|
|
|
|
struct uio *auio;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = freebsd32_copyinuio(uap->iovp, uap->iovcnt, &auio);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
2010-03-11 14:49:06 +00:00
|
|
|
error = kern_pwritev(td, uap->fd, auio, PAIR32TO64(off_t,uap->offset));
|
2005-07-07 18:17:55 +00:00
|
|
|
free(auio, M_IOV);
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2010-03-19 10:49:03 +00:00
|
|
|
int
|
2005-10-31 21:09:56 +00:00
|
|
|
freebsd32_copyiniov(struct iovec32 *iovp32, u_int iovcnt, struct iovec **iovp,
|
2005-10-15 05:57:06 +00:00
|
|
|
int error)
|
|
|
|
{
|
|
|
|
struct iovec32 iov32;
|
2005-10-31 21:09:56 +00:00
|
|
|
struct iovec *iov;
|
2005-10-15 05:57:06 +00:00
|
|
|
u_int iovlen;
|
2005-10-31 21:09:56 +00:00
|
|
|
int i;
|
2005-10-15 05:57:06 +00:00
|
|
|
|
2005-10-31 21:09:56 +00:00
|
|
|
*iovp = NULL;
|
2005-10-15 05:57:06 +00:00
|
|
|
if (iovcnt > UIO_MAXIOV)
|
|
|
|
return (error);
|
|
|
|
iovlen = iovcnt * sizeof(struct iovec);
|
2005-10-31 21:09:56 +00:00
|
|
|
iov = malloc(iovlen, M_IOV, M_WAITOK);
|
2005-10-15 05:57:06 +00:00
|
|
|
for (i = 0; i < iovcnt; i++) {
|
2005-10-31 21:09:56 +00:00
|
|
|
error = copyin(&iovp32[i], &iov32, sizeof(struct iovec32));
|
2005-10-15 05:57:06 +00:00
|
|
|
if (error) {
|
2005-10-31 21:09:56 +00:00
|
|
|
free(iov, M_IOV);
|
2005-10-15 05:57:06 +00:00
|
|
|
return (error);
|
|
|
|
}
|
2005-10-31 21:09:56 +00:00
|
|
|
iov[i].iov_base = PTRIN(iov32.iov_base);
|
|
|
|
iov[i].iov_len = iov32.iov_len;
|
|
|
|
}
|
|
|
|
*iovp = iov;
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
2005-10-15 05:57:06 +00:00
|
|
|
static int
|
|
|
|
freebsd32_copyinmsghdr(struct msghdr32 *msg32, struct msghdr *msg)
|
|
|
|
{
|
|
|
|
struct msghdr32 m32;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = copyin(msg32, &m32, sizeof(m32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
msg->msg_name = PTRIN(m32.msg_name);
|
|
|
|
msg->msg_namelen = m32.msg_namelen;
|
|
|
|
msg->msg_iov = PTRIN(m32.msg_iov);
|
|
|
|
msg->msg_iovlen = m32.msg_iovlen;
|
|
|
|
msg->msg_control = PTRIN(m32.msg_control);
|
|
|
|
msg->msg_controllen = m32.msg_controllen;
|
|
|
|
msg->msg_flags = m32.msg_flags;
|
2005-10-31 21:09:56 +00:00
|
|
|
return (0);
|
2005-10-15 05:57:06 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
static int
|
|
|
|
freebsd32_copyoutmsghdr(struct msghdr *msg, struct msghdr32 *msg32)
|
|
|
|
{
|
|
|
|
struct msghdr32 m32;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
m32.msg_name = PTROUT(msg->msg_name);
|
|
|
|
m32.msg_namelen = msg->msg_namelen;
|
|
|
|
m32.msg_iov = PTROUT(msg->msg_iov);
|
|
|
|
m32.msg_iovlen = msg->msg_iovlen;
|
|
|
|
m32.msg_control = PTROUT(msg->msg_control);
|
|
|
|
m32.msg_controllen = msg->msg_controllen;
|
|
|
|
m32.msg_flags = msg->msg_flags;
|
|
|
|
error = copyout(&m32, msg32, sizeof(m32));
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2012-03-03 21:39:12 +00:00
|
|
|
#ifndef __mips__
|
2005-10-31 21:09:56 +00:00
|
|
|
#define FREEBSD32_ALIGNBYTES (sizeof(int) - 1)
|
2012-03-03 21:39:12 +00:00
|
|
|
#else
|
|
|
|
#define FREEBSD32_ALIGNBYTES (sizeof(long) - 1)
|
|
|
|
#endif
|
2005-10-31 21:09:56 +00:00
|
|
|
#define FREEBSD32_ALIGN(p) \
|
|
|
|
(((u_long)(p) + FREEBSD32_ALIGNBYTES) & ~FREEBSD32_ALIGNBYTES)
|
|
|
|
#define FREEBSD32_CMSG_SPACE(l) \
|
|
|
|
(FREEBSD32_ALIGN(sizeof(struct cmsghdr)) + FREEBSD32_ALIGN(l))
|
|
|
|
|
|
|
|
#define FREEBSD32_CMSG_DATA(cmsg) ((unsigned char *)(cmsg) + \
|
|
|
|
FREEBSD32_ALIGN(sizeof(struct cmsghdr)))
|
2017-09-07 04:29:57 +00:00
|
|
|
|
|
|
|
static size_t
|
2018-08-07 16:36:48 +00:00
|
|
|
freebsd32_cmsg_convert(const struct cmsghdr *cm, void *data, socklen_t datalen)
|
2017-09-07 04:29:57 +00:00
|
|
|
{
|
|
|
|
size_t copylen;
|
|
|
|
union {
|
|
|
|
struct timespec32 ts;
|
|
|
|
struct timeval32 tv;
|
|
|
|
struct bintime32 bt;
|
|
|
|
} tmp32;
|
|
|
|
|
|
|
|
union {
|
|
|
|
struct timespec ts;
|
|
|
|
struct timeval tv;
|
|
|
|
struct bintime bt;
|
|
|
|
} *in;
|
|
|
|
|
|
|
|
in = data;
|
|
|
|
copylen = 0;
|
|
|
|
switch (cm->cmsg_level) {
|
|
|
|
case SOL_SOCKET:
|
|
|
|
switch (cm->cmsg_type) {
|
|
|
|
case SCM_TIMESTAMP:
|
|
|
|
TV_CP(*in, tmp32, tv);
|
|
|
|
copylen = sizeof(tmp32.tv);
|
|
|
|
break;
|
|
|
|
|
|
|
|
case SCM_BINTIME:
|
|
|
|
BT_CP(*in, tmp32, bt);
|
|
|
|
copylen = sizeof(tmp32.bt);
|
|
|
|
break;
|
|
|
|
|
|
|
|
case SCM_REALTIME:
|
|
|
|
case SCM_MONOTONIC:
|
|
|
|
TS_CP(*in, tmp32, ts);
|
|
|
|
copylen = sizeof(tmp32.ts);
|
|
|
|
break;
|
|
|
|
|
|
|
|
default:
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
default:
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (copylen == 0)
|
|
|
|
return (datalen);
|
|
|
|
|
|
|
|
KASSERT((datalen >= copylen), ("corrupted cmsghdr"));
|
|
|
|
|
|
|
|
bcopy(&tmp32, data, copylen);
|
|
|
|
return (copylen);
|
|
|
|
}
|
|
|
|
|
2005-10-31 21:09:56 +00:00
|
|
|
static int
|
|
|
|
freebsd32_copy_msg_out(struct msghdr *msg, struct mbuf *control)
|
|
|
|
{
|
|
|
|
struct cmsghdr *cm;
|
|
|
|
void *data;
|
2018-08-07 16:36:48 +00:00
|
|
|
socklen_t clen, datalen, datalen_out, oldclen;
|
2005-10-31 21:09:56 +00:00
|
|
|
int error;
|
|
|
|
caddr_t ctlbuf;
|
|
|
|
int len, maxlen, copylen;
|
|
|
|
struct mbuf *m;
|
|
|
|
error = 0;
|
|
|
|
|
|
|
|
len = msg->msg_controllen;
|
|
|
|
maxlen = msg->msg_controllen;
|
|
|
|
msg->msg_controllen = 0;
|
|
|
|
|
|
|
|
ctlbuf = msg->msg_control;
|
2018-08-07 16:36:48 +00:00
|
|
|
for (m = control; m != NULL && len > 0; m = m->m_next) {
|
2005-10-31 21:09:56 +00:00
|
|
|
cm = mtod(m, struct cmsghdr *);
|
|
|
|
clen = m->m_len;
|
|
|
|
while (cm != NULL) {
|
|
|
|
if (sizeof(struct cmsghdr) > clen ||
|
|
|
|
cm->cmsg_len > clen) {
|
|
|
|
error = EINVAL;
|
|
|
|
break;
|
2017-09-07 04:29:57 +00:00
|
|
|
}
|
2005-10-31 21:09:56 +00:00
|
|
|
|
|
|
|
data = CMSG_DATA(cm);
|
|
|
|
datalen = (caddr_t)cm + cm->cmsg_len - (caddr_t)data;
|
2017-09-07 04:29:57 +00:00
|
|
|
datalen_out = freebsd32_cmsg_convert(cm, data, datalen);
|
2005-10-31 21:09:56 +00:00
|
|
|
|
2018-08-07 16:36:48 +00:00
|
|
|
/*
|
|
|
|
* Copy out the message header. Preserve the native
|
|
|
|
* message size in case we need to inspect the message
|
|
|
|
* contents later.
|
|
|
|
*/
|
2005-10-31 21:09:56 +00:00
|
|
|
copylen = sizeof(struct cmsghdr);
|
|
|
|
if (len < copylen) {
|
|
|
|
msg->msg_flags |= MSG_CTRUNC;
|
2018-08-07 16:36:48 +00:00
|
|
|
m_dispose_extcontrolm(m);
|
|
|
|
goto exit;
|
2005-10-31 21:09:56 +00:00
|
|
|
}
|
2018-08-07 16:36:48 +00:00
|
|
|
oldclen = cm->cmsg_len;
|
|
|
|
cm->cmsg_len = FREEBSD32_ALIGN(sizeof(struct cmsghdr)) +
|
|
|
|
datalen_out;
|
2017-09-07 04:29:57 +00:00
|
|
|
error = copyout(cm, ctlbuf, copylen);
|
2018-08-07 16:36:48 +00:00
|
|
|
cm->cmsg_len = oldclen;
|
|
|
|
if (error != 0)
|
2005-10-31 21:09:56 +00:00
|
|
|
goto exit;
|
|
|
|
|
|
|
|
ctlbuf += FREEBSD32_ALIGN(copylen);
|
|
|
|
len -= FREEBSD32_ALIGN(copylen);
|
|
|
|
|
2017-09-07 04:29:57 +00:00
|
|
|
copylen = datalen_out;
|
2005-10-31 21:09:56 +00:00
|
|
|
if (len < copylen) {
|
|
|
|
msg->msg_flags |= MSG_CTRUNC;
|
2018-08-07 16:36:48 +00:00
|
|
|
m_dispose_extcontrolm(m);
|
|
|
|
break;
|
2005-10-31 21:09:56 +00:00
|
|
|
}
|
|
|
|
|
2018-08-07 16:36:48 +00:00
|
|
|
/* Copy out the message data. */
|
2017-09-07 04:29:57 +00:00
|
|
|
error = copyout(data, ctlbuf, copylen);
|
2005-10-31 21:09:56 +00:00
|
|
|
if (error)
|
|
|
|
goto exit;
|
|
|
|
|
|
|
|
ctlbuf += FREEBSD32_ALIGN(copylen);
|
|
|
|
len -= FREEBSD32_ALIGN(copylen);
|
|
|
|
|
|
|
|
if (CMSG_SPACE(datalen) < clen) {
|
|
|
|
clen -= CMSG_SPACE(datalen);
|
|
|
|
cm = (struct cmsghdr *)
|
2018-08-07 16:36:48 +00:00
|
|
|
((caddr_t)cm + CMSG_SPACE(datalen));
|
2005-10-31 21:09:56 +00:00
|
|
|
} else {
|
|
|
|
clen = 0;
|
|
|
|
cm = NULL;
|
|
|
|
}
|
2018-08-07 16:36:48 +00:00
|
|
|
|
2019-03-30 23:43:58 +00:00
|
|
|
msg->msg_controllen +=
|
|
|
|
FREEBSD32_CMSG_SPACE(datalen_out);
|
2018-08-07 16:36:48 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
if (len == 0 && m != NULL) {
|
|
|
|
msg->msg_flags |= MSG_CTRUNC;
|
|
|
|
m_dispose_extcontrolm(m);
|
2005-10-31 21:09:56 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
exit:
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2005-10-15 05:57:06 +00:00
|
|
|
int
|
|
|
|
freebsd32_recvmsg(td, uap)
|
|
|
|
struct thread *td;
|
|
|
|
struct freebsd32_recvmsg_args /* {
|
|
|
|
int s;
|
|
|
|
struct msghdr32 *msg;
|
|
|
|
int flags;
|
|
|
|
} */ *uap;
|
|
|
|
{
|
|
|
|
struct msghdr msg;
|
|
|
|
struct msghdr32 m32;
|
|
|
|
struct iovec *uiov, *iov;
|
2005-10-31 21:09:56 +00:00
|
|
|
struct mbuf *control = NULL;
|
|
|
|
struct mbuf **controlp;
|
2005-10-15 05:57:06 +00:00
|
|
|
|
2005-10-31 21:09:56 +00:00
|
|
|
int error;
|
2005-10-15 05:57:06 +00:00
|
|
|
error = copyin(uap->msg, &m32, sizeof(m32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
error = freebsd32_copyinmsghdr(uap->msg, &msg);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
2006-07-10 19:37:43 +00:00
|
|
|
error = freebsd32_copyiniov(PTRIN(m32.msg_iov), m32.msg_iovlen, &iov,
|
|
|
|
EMSGSIZE);
|
2005-10-15 05:57:06 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
msg.msg_flags = uap->flags;
|
|
|
|
uiov = msg.msg_iov;
|
|
|
|
msg.msg_iov = iov;
|
2005-10-31 21:09:56 +00:00
|
|
|
|
|
|
|
controlp = (msg.msg_control != NULL) ? &control : NULL;
|
2006-07-10 21:38:17 +00:00
|
|
|
error = kern_recvit(td, uap->s, &msg, UIO_USERSPACE, controlp);
|
2005-10-15 05:57:06 +00:00
|
|
|
if (error == 0) {
|
|
|
|
msg.msg_iov = uiov;
|
2018-08-07 16:36:48 +00:00
|
|
|
|
2005-10-31 21:09:56 +00:00
|
|
|
if (control != NULL)
|
|
|
|
error = freebsd32_copy_msg_out(&msg, control);
|
2010-08-03 11:23:44 +00:00
|
|
|
else
|
|
|
|
msg.msg_controllen = 0;
|
2018-08-07 16:36:48 +00:00
|
|
|
|
2005-10-31 21:09:56 +00:00
|
|
|
if (error == 0)
|
|
|
|
error = freebsd32_copyoutmsghdr(&msg, uap->msg);
|
2005-10-15 05:57:06 +00:00
|
|
|
}
|
|
|
|
free(iov, M_IOV);
|
2005-10-31 21:09:56 +00:00
|
|
|
|
2018-08-07 16:36:48 +00:00
|
|
|
if (control != NULL) {
|
|
|
|
if (error != 0)
|
|
|
|
m_dispose_extcontrolm(control);
|
2005-10-31 21:09:56 +00:00
|
|
|
m_freem(control);
|
2018-08-07 16:36:48 +00:00
|
|
|
}
|
2005-10-31 21:09:56 +00:00
|
|
|
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2014-04-05 18:56:01 +00:00
|
|
|
/*
|
|
|
|
* Copy-in the array of control messages constructed using alignment
|
|
|
|
* and padding suitable for a 32-bit environment and construct an
|
|
|
|
* mbuf using alignment and padding suitable for a 64-bit kernel.
|
|
|
|
* The alignment and padding are defined indirectly by CMSG_DATA(),
|
|
|
|
* CMSG_SPACE() and CMSG_LEN().
|
|
|
|
*/
|
2005-10-31 21:09:56 +00:00
|
|
|
static int
|
2014-04-05 18:56:01 +00:00
|
|
|
freebsd32_copyin_control(struct mbuf **mp, caddr_t buf, u_int buflen)
|
2005-10-31 21:09:56 +00:00
|
|
|
{
|
2014-04-05 18:56:01 +00:00
|
|
|
struct mbuf *m;
|
|
|
|
void *md;
|
|
|
|
u_int idx, len, msglen;
|
2005-10-31 21:09:56 +00:00
|
|
|
int error;
|
|
|
|
|
2014-04-05 18:56:01 +00:00
|
|
|
buflen = FREEBSD32_ALIGN(buflen);
|
2005-10-31 21:09:56 +00:00
|
|
|
|
2014-04-05 18:56:01 +00:00
|
|
|
if (buflen > MCLBYTES)
|
|
|
|
return (EINVAL);
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Iterate over the buffer and get the length of each message
|
|
|
|
* in there. This has 32-bit alignment and padding. Use it to
|
|
|
|
* determine the length of these messages when using 64-bit
|
|
|
|
* alignment and padding.
|
|
|
|
*/
|
|
|
|
idx = 0;
|
|
|
|
len = 0;
|
|
|
|
while (idx < buflen) {
|
|
|
|
error = copyin(buf + idx, &msglen, sizeof(msglen));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
if (msglen < sizeof(struct cmsghdr))
|
|
|
|
return (EINVAL);
|
|
|
|
msglen = FREEBSD32_ALIGN(msglen);
|
|
|
|
if (idx + msglen > buflen)
|
|
|
|
return (EINVAL);
|
|
|
|
idx += msglen;
|
|
|
|
msglen += CMSG_ALIGN(sizeof(struct cmsghdr)) -
|
|
|
|
FREEBSD32_ALIGN(sizeof(struct cmsghdr));
|
|
|
|
len += CMSG_ALIGN(msglen);
|
|
|
|
}
|
|
|
|
|
|
|
|
if (len > MCLBYTES)
|
|
|
|
return (EINVAL);
|
|
|
|
|
|
|
|
m = m_get(M_WAITOK, MT_CONTROL);
|
|
|
|
if (len > MLEN)
|
|
|
|
MCLGET(m, M_WAITOK);
|
|
|
|
m->m_len = len;
|
|
|
|
|
|
|
|
md = mtod(m, void *);
|
|
|
|
while (buflen > 0) {
|
|
|
|
error = copyin(buf, md, sizeof(struct cmsghdr));
|
|
|
|
if (error)
|
2005-10-31 21:09:56 +00:00
|
|
|
break;
|
2014-04-05 18:56:01 +00:00
|
|
|
msglen = *(u_int *)md;
|
|
|
|
msglen = FREEBSD32_ALIGN(msglen);
|
2005-10-31 21:09:56 +00:00
|
|
|
|
2014-04-05 18:56:01 +00:00
|
|
|
/* Modify the message length to account for alignment. */
|
|
|
|
*(u_int *)md = msglen + CMSG_ALIGN(sizeof(struct cmsghdr)) -
|
|
|
|
FREEBSD32_ALIGN(sizeof(struct cmsghdr));
|
2005-10-31 21:09:56 +00:00
|
|
|
|
2014-04-05 18:56:01 +00:00
|
|
|
md = (char *)md + CMSG_ALIGN(sizeof(struct cmsghdr));
|
|
|
|
buf += FREEBSD32_ALIGN(sizeof(struct cmsghdr));
|
|
|
|
buflen -= FREEBSD32_ALIGN(sizeof(struct cmsghdr));
|
2005-10-31 21:09:56 +00:00
|
|
|
|
2014-04-05 18:56:01 +00:00
|
|
|
msglen -= FREEBSD32_ALIGN(sizeof(struct cmsghdr));
|
|
|
|
if (msglen > 0) {
|
|
|
|
error = copyin(buf, md, msglen);
|
|
|
|
if (error)
|
|
|
|
break;
|
|
|
|
md = (char *)md + CMSG_ALIGN(msglen);
|
|
|
|
buf += msglen;
|
|
|
|
buflen -= msglen;
|
2005-10-31 21:09:56 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-04-05 18:56:01 +00:00
|
|
|
if (error)
|
|
|
|
m_free(m);
|
|
|
|
else
|
|
|
|
*mp = m;
|
2005-10-15 05:57:06 +00:00
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_sendmsg(struct thread *td,
|
|
|
|
struct freebsd32_sendmsg_args *uap)
|
|
|
|
{
|
|
|
|
struct msghdr msg;
|
|
|
|
struct msghdr32 m32;
|
|
|
|
struct iovec *iov;
|
2005-10-31 21:09:56 +00:00
|
|
|
struct mbuf *control = NULL;
|
|
|
|
struct sockaddr *to = NULL;
|
2005-10-15 05:57:06 +00:00
|
|
|
int error;
|
|
|
|
|
|
|
|
error = copyin(uap->msg, &m32, sizeof(m32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
error = freebsd32_copyinmsghdr(uap->msg, &msg);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
2006-07-10 19:37:43 +00:00
|
|
|
error = freebsd32_copyiniov(PTRIN(m32.msg_iov), m32.msg_iovlen, &iov,
|
|
|
|
EMSGSIZE);
|
2005-10-15 05:57:06 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
msg.msg_iov = iov;
|
2005-10-31 21:09:56 +00:00
|
|
|
if (msg.msg_name != NULL) {
|
|
|
|
error = getsockaddr(&to, msg.msg_name, msg.msg_namelen);
|
|
|
|
if (error) {
|
|
|
|
to = NULL;
|
|
|
|
goto out;
|
|
|
|
}
|
|
|
|
msg.msg_name = to;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (msg.msg_control) {
|
|
|
|
if (msg.msg_controllen < sizeof(struct cmsghdr)) {
|
|
|
|
error = EINVAL;
|
|
|
|
goto out;
|
|
|
|
}
|
|
|
|
|
2014-04-05 18:56:01 +00:00
|
|
|
error = freebsd32_copyin_control(&control, msg.msg_control,
|
|
|
|
msg.msg_controllen);
|
2005-10-31 21:09:56 +00:00
|
|
|
if (error)
|
|
|
|
goto out;
|
2014-04-05 18:56:01 +00:00
|
|
|
|
|
|
|
msg.msg_control = NULL;
|
|
|
|
msg.msg_controllen = 0;
|
2005-10-31 21:09:56 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
error = kern_sendit(td, uap->s, &msg, uap->flags, control,
|
|
|
|
UIO_USERSPACE);
|
|
|
|
|
|
|
|
out:
|
2005-10-15 05:57:06 +00:00
|
|
|
free(iov, M_IOV);
|
2005-10-31 21:09:56 +00:00
|
|
|
if (to)
|
|
|
|
free(to, M_SONAME);
|
2005-10-15 05:57:06 +00:00
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_recvfrom(struct thread *td,
|
|
|
|
struct freebsd32_recvfrom_args *uap)
|
|
|
|
{
|
|
|
|
struct msghdr msg;
|
|
|
|
struct iovec aiov;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->fromlenaddr) {
|
2006-07-10 19:37:43 +00:00
|
|
|
error = copyin(PTRIN(uap->fromlenaddr), &msg.msg_namelen,
|
|
|
|
sizeof(msg.msg_namelen));
|
2005-10-15 05:57:06 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
} else {
|
|
|
|
msg.msg_namelen = 0;
|
|
|
|
}
|
|
|
|
|
2006-07-10 19:37:43 +00:00
|
|
|
msg.msg_name = PTRIN(uap->from);
|
2005-10-15 05:57:06 +00:00
|
|
|
msg.msg_iov = &aiov;
|
|
|
|
msg.msg_iovlen = 1;
|
2006-07-10 19:37:43 +00:00
|
|
|
aiov.iov_base = PTRIN(uap->buf);
|
2005-10-15 05:57:06 +00:00
|
|
|
aiov.iov_len = uap->len;
|
2006-07-10 19:37:43 +00:00
|
|
|
msg.msg_control = NULL;
|
2005-10-15 05:57:06 +00:00
|
|
|
msg.msg_flags = uap->flags;
|
2006-07-10 21:38:17 +00:00
|
|
|
error = kern_recvit(td, uap->s, &msg, UIO_USERSPACE, NULL);
|
|
|
|
if (error == 0 && uap->fromlenaddr)
|
|
|
|
error = copyout(&msg.msg_namelen, PTRIN(uap->fromlenaddr),
|
|
|
|
sizeof (msg.msg_namelen));
|
2005-10-15 05:57:06 +00:00
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_settimeofday(struct thread *td,
|
|
|
|
struct freebsd32_settimeofday_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2005-03-31 22:58:13 +00:00
|
|
|
struct timeval32 tv32;
|
|
|
|
struct timeval tv, *tvp;
|
|
|
|
struct timezone tz, *tzp;
|
2002-07-20 02:56:12 +00:00
|
|
|
int error;
|
|
|
|
|
2005-03-31 22:58:13 +00:00
|
|
|
if (uap->tv) {
|
|
|
|
error = copyin(uap->tv, &tv32, sizeof(tv32));
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
2005-03-31 22:58:13 +00:00
|
|
|
CP(tv32, tv, tv_sec);
|
|
|
|
CP(tv32, tv, tv_usec);
|
|
|
|
tvp = &tv;
|
|
|
|
} else
|
|
|
|
tvp = NULL;
|
|
|
|
if (uap->tzp) {
|
|
|
|
error = copyin(uap->tzp, &tz, sizeof(tz));
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
2005-03-31 22:58:13 +00:00
|
|
|
tzp = &tz;
|
|
|
|
} else
|
|
|
|
tzp = NULL;
|
|
|
|
return (kern_settimeofday(td, tvp, tzp));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_utimes(struct thread *td, struct freebsd32_utimes_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
struct timeval32 s32[2];
|
|
|
|
struct timeval s[2], *sp;
|
2002-07-20 02:56:12 +00:00
|
|
|
int error;
|
|
|
|
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
if (uap->tptr != NULL) {
|
|
|
|
error = copyin(uap->tptr, s32, sizeof(s32));
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
CP(s32[0], s[0], tv_sec);
|
|
|
|
CP(s32[0], s[0], tv_usec);
|
|
|
|
CP(s32[1], s[1], tv_sec);
|
|
|
|
CP(s32[1], s[1], tv_usec);
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
sp = s;
|
|
|
|
} else
|
|
|
|
sp = NULL;
|
2014-11-13 18:01:51 +00:00
|
|
|
return (kern_utimesat(td, AT_FDCWD, uap->path, UIO_USERSPACE,
|
|
|
|
sp, UIO_SYSSPACE));
|
2006-01-20 16:22:06 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_lutimes(struct thread *td, struct freebsd32_lutimes_args *uap)
|
|
|
|
{
|
|
|
|
struct timeval32 s32[2];
|
|
|
|
struct timeval s[2], *sp;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->tptr != NULL) {
|
|
|
|
error = copyin(uap->tptr, s32, sizeof(s32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
CP(s32[0], s[0], tv_sec);
|
|
|
|
CP(s32[0], s[0], tv_usec);
|
|
|
|
CP(s32[1], s[1], tv_sec);
|
|
|
|
CP(s32[1], s[1], tv_usec);
|
|
|
|
sp = s;
|
|
|
|
} else
|
|
|
|
sp = NULL;
|
|
|
|
return (kern_lutimes(td, uap->path, UIO_USERSPACE, sp, UIO_SYSSPACE));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
2005-12-08 22:14:25 +00:00
|
|
|
int
|
|
|
|
freebsd32_futimes(struct thread *td, struct freebsd32_futimes_args *uap)
|
|
|
|
{
|
|
|
|
struct timeval32 s32[2];
|
|
|
|
struct timeval s[2], *sp;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->tptr != NULL) {
|
|
|
|
error = copyin(uap->tptr, s32, sizeof(s32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
CP(s32[0], s[0], tv_sec);
|
|
|
|
CP(s32[0], s[0], tv_usec);
|
|
|
|
CP(s32[1], s[1], tv_sec);
|
|
|
|
CP(s32[1], s[1], tv_usec);
|
|
|
|
sp = s;
|
|
|
|
} else
|
|
|
|
sp = NULL;
|
|
|
|
return (kern_futimes(td, uap->fd, sp, UIO_SYSSPACE));
|
|
|
|
}
|
|
|
|
|
2008-03-31 12:08:30 +00:00
|
|
|
int
|
|
|
|
freebsd32_futimesat(struct thread *td, struct freebsd32_futimesat_args *uap)
|
|
|
|
{
|
|
|
|
struct timeval32 s32[2];
|
|
|
|
struct timeval s[2], *sp;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->times != NULL) {
|
|
|
|
error = copyin(uap->times, s32, sizeof(s32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
CP(s32[0], s[0], tv_sec);
|
|
|
|
CP(s32[0], s[0], tv_usec);
|
|
|
|
CP(s32[1], s[1], tv_sec);
|
|
|
|
CP(s32[1], s[1], tv_usec);
|
|
|
|
sp = s;
|
|
|
|
} else
|
|
|
|
sp = NULL;
|
|
|
|
return (kern_utimesat(td, uap->fd, uap->path, UIO_USERSPACE,
|
|
|
|
sp, UIO_SYSSPACE));
|
|
|
|
}
|
2005-12-08 22:14:25 +00:00
|
|
|
|
2015-01-23 21:07:08 +00:00
|
|
|
int
|
|
|
|
freebsd32_futimens(struct thread *td, struct freebsd32_futimens_args *uap)
|
|
|
|
{
|
|
|
|
struct timespec32 ts32[2];
|
|
|
|
struct timespec ts[2], *tsp;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->times != NULL) {
|
|
|
|
error = copyin(uap->times, ts32, sizeof(ts32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
CP(ts32[0], ts[0], tv_sec);
|
|
|
|
CP(ts32[0], ts[0], tv_nsec);
|
|
|
|
CP(ts32[1], ts[1], tv_sec);
|
|
|
|
CP(ts32[1], ts[1], tv_nsec);
|
|
|
|
tsp = ts;
|
|
|
|
} else
|
|
|
|
tsp = NULL;
|
|
|
|
return (kern_futimens(td, uap->fd, tsp, UIO_SYSSPACE));
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_utimensat(struct thread *td, struct freebsd32_utimensat_args *uap)
|
|
|
|
{
|
|
|
|
struct timespec32 ts32[2];
|
|
|
|
struct timespec ts[2], *tsp;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->times != NULL) {
|
|
|
|
error = copyin(uap->times, ts32, sizeof(ts32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
CP(ts32[0], ts[0], tv_sec);
|
|
|
|
CP(ts32[0], ts[0], tv_nsec);
|
|
|
|
CP(ts32[1], ts[1], tv_sec);
|
|
|
|
CP(ts32[1], ts[1], tv_nsec);
|
|
|
|
tsp = ts;
|
|
|
|
} else
|
|
|
|
tsp = NULL;
|
|
|
|
return (kern_utimensat(td, uap->fd, uap->path, UIO_USERSPACE,
|
|
|
|
tsp, UIO_SYSSPACE, uap->flag));
|
|
|
|
}
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_adjtime(struct thread *td, struct freebsd32_adjtime_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2005-03-31 22:58:13 +00:00
|
|
|
struct timeval32 tv32;
|
|
|
|
struct timeval delta, olddelta, *deltap;
|
2002-07-20 02:56:12 +00:00
|
|
|
int error;
|
|
|
|
|
2005-03-31 22:58:13 +00:00
|
|
|
if (uap->delta) {
|
|
|
|
error = copyin(uap->delta, &tv32, sizeof(tv32));
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
2005-03-31 22:58:13 +00:00
|
|
|
CP(tv32, delta, tv_sec);
|
|
|
|
CP(tv32, delta, tv_usec);
|
|
|
|
deltap = δ
|
|
|
|
} else
|
|
|
|
deltap = NULL;
|
|
|
|
error = kern_adjtime(td, deltap, &olddelta);
|
|
|
|
if (uap->olddelta && error == 0) {
|
|
|
|
CP(olddelta, tv32, tv_sec);
|
|
|
|
CP(olddelta, tv32, tv_usec);
|
|
|
|
error = copyout(&tv32, uap->olddelta, sizeof(tv32));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2004-04-24 04:31:59 +00:00
|
|
|
#ifdef COMPAT_FREEBSD4
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2004-04-14 23:17:37 +00:00
|
|
|
freebsd4_freebsd32_statfs(struct thread *td, struct freebsd4_freebsd32_statfs_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
struct statfs32 s32;
|
2017-01-05 17:19:26 +00:00
|
|
|
struct statfs *sp;
|
2002-07-20 02:56:12 +00:00
|
|
|
int error;
|
|
|
|
|
2017-01-05 17:19:26 +00:00
|
|
|
sp = malloc(sizeof(struct statfs), M_STATFS, M_WAITOK);
|
|
|
|
error = kern_statfs(td, uap->path, UIO_USERSPACE, sp);
|
|
|
|
if (error == 0) {
|
|
|
|
copy_statfs(sp, &s32);
|
|
|
|
error = copyout(&s32, uap->buf, sizeof(s32));
|
|
|
|
}
|
|
|
|
free(sp, M_STATFS);
|
|
|
|
return (error);
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
2004-04-24 04:31:59 +00:00
|
|
|
#endif
|
2002-07-20 02:56:12 +00:00
|
|
|
|
2004-04-24 04:31:59 +00:00
|
|
|
#ifdef COMPAT_FREEBSD4
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2004-04-14 23:17:37 +00:00
|
|
|
freebsd4_freebsd32_fstatfs(struct thread *td, struct freebsd4_freebsd32_fstatfs_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
struct statfs32 s32;
|
2017-01-05 17:19:26 +00:00
|
|
|
struct statfs *sp;
|
2002-07-20 02:56:12 +00:00
|
|
|
int error;
|
|
|
|
|
2017-01-05 17:19:26 +00:00
|
|
|
sp = malloc(sizeof(struct statfs), M_STATFS, M_WAITOK);
|
|
|
|
error = kern_fstatfs(td, uap->fd, sp);
|
|
|
|
if (error == 0) {
|
|
|
|
copy_statfs(sp, &s32);
|
|
|
|
error = copyout(&s32, uap->buf, sizeof(s32));
|
|
|
|
}
|
|
|
|
free(sp, M_STATFS);
|
|
|
|
return (error);
|
2004-04-14 23:17:37 +00:00
|
|
|
}
|
2004-04-24 04:31:59 +00:00
|
|
|
#endif
|
2004-04-14 23:17:37 +00:00
|
|
|
|
2004-04-24 04:31:59 +00:00
|
|
|
#ifdef COMPAT_FREEBSD4
|
2004-04-14 23:17:37 +00:00
|
|
|
int
|
|
|
|
freebsd4_freebsd32_fhstatfs(struct thread *td, struct freebsd4_freebsd32_fhstatfs_args *uap)
|
|
|
|
{
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
struct statfs32 s32;
|
2017-01-05 17:19:26 +00:00
|
|
|
struct statfs *sp;
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
fhandle_t fh;
|
2004-04-14 23:17:37 +00:00
|
|
|
int error;
|
|
|
|
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
if ((error = copyin(uap->u_fhp, &fh, sizeof(fhandle_t))) != 0)
|
|
|
|
return (error);
|
2017-01-05 17:19:26 +00:00
|
|
|
sp = malloc(sizeof(struct statfs), M_STATFS, M_WAITOK);
|
|
|
|
error = kern_fhstatfs(td, fh, sp);
|
|
|
|
if (error == 0) {
|
|
|
|
copy_statfs(sp, &s32);
|
|
|
|
error = copyout(&s32, uap->buf, sizeof(s32));
|
|
|
|
}
|
|
|
|
free(sp, M_STATFS);
|
|
|
|
return (error);
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
2004-04-24 04:31:59 +00:00
|
|
|
#endif
|
2002-07-20 02:56:12 +00:00
|
|
|
|
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_pread(struct thread *td, struct freebsd32_pread_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
|
|
|
|
2017-01-31 15:35:18 +00:00
|
|
|
return (kern_pread(td, uap->fd, uap->buf, uap->nbyte,
|
|
|
|
PAIR32TO64(off_t, uap->offset)));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_pwrite(struct thread *td, struct freebsd32_pwrite_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
|
|
|
|
2017-01-31 15:35:18 +00:00
|
|
|
return (kern_pwrite(td, uap->fd, uap->buf, uap->nbyte,
|
|
|
|
PAIR32TO64(off_t, uap->offset)));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
2011-06-16 22:05:56 +00:00
|
|
|
#ifdef COMPAT_43
|
|
|
|
int
|
|
|
|
ofreebsd32_lseek(struct thread *td, struct ofreebsd32_lseek_args *uap)
|
|
|
|
{
|
|
|
|
|
2017-01-30 12:24:47 +00:00
|
|
|
return (kern_lseek(td, uap->fd, uap->offset, uap->whence));
|
2011-06-16 22:05:56 +00:00
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_lseek(struct thread *td, struct freebsd32_lseek_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
|
|
|
int error;
|
|
|
|
off_t pos;
|
|
|
|
|
2017-01-30 12:24:47 +00:00
|
|
|
error = kern_lseek(td, uap->fd, PAIR32TO64(off_t, uap->offset),
|
|
|
|
uap->whence);
|
2002-07-20 02:56:12 +00:00
|
|
|
/* Expand the quad return into two parts for eax and edx */
|
2014-03-16 00:53:40 +00:00
|
|
|
pos = td->td_uretoff.tdu_off;
|
2010-03-11 14:49:06 +00:00
|
|
|
td->td_retval[RETVAL_LO] = pos & 0xffffffff; /* %eax */
|
|
|
|
td->td_retval[RETVAL_HI] = pos >> 32; /* %edx */
|
2002-07-20 02:56:12 +00:00
|
|
|
return error;
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_truncate(struct thread *td, struct freebsd32_truncate_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
|
|
|
|
2017-01-31 15:19:44 +00:00
|
|
|
return (kern_truncate(td, uap->path, UIO_USERSPACE,
|
|
|
|
PAIR32TO64(off_t, uap->length)));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_ftruncate(struct thread *td, struct freebsd32_ftruncate_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
|
|
|
|
2017-01-30 11:50:54 +00:00
|
|
|
return (kern_ftruncate(td, uap->fd, PAIR32TO64(off_t, uap->length)));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
2011-04-01 11:16:29 +00:00
|
|
|
#ifdef COMPAT_43
|
|
|
|
int
|
|
|
|
ofreebsd32_getdirentries(struct thread *td,
|
|
|
|
struct ofreebsd32_getdirentries_args *uap)
|
|
|
|
{
|
|
|
|
struct ogetdirentries_args ap;
|
|
|
|
int error;
|
|
|
|
long loff;
|
|
|
|
int32_t loff_cut;
|
|
|
|
|
|
|
|
ap.fd = uap->fd;
|
|
|
|
ap.buf = uap->buf;
|
|
|
|
ap.count = uap->count;
|
|
|
|
ap.basep = NULL;
|
|
|
|
error = kern_ogetdirentries(td, &ap, &loff);
|
|
|
|
if (error == 0) {
|
|
|
|
loff_cut = loff;
|
|
|
|
error = copyout(&loff_cut, uap->basep, sizeof(int32_t));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
#if defined(COMPAT_FREEBSD11)
|
|
|
|
int
|
|
|
|
freebsd11_freebsd32_getdirentries(struct thread *td,
|
|
|
|
struct freebsd11_freebsd32_getdirentries_args *uap)
|
|
|
|
{
|
|
|
|
long base;
|
|
|
|
int32_t base32;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = freebsd11_kern_getdirentries(td, uap->fd, uap->buf, uap->count,
|
|
|
|
&base, NULL);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
if (uap->basep != NULL) {
|
|
|
|
base32 = base;
|
|
|
|
error = copyout(&base32, uap->basep, sizeof(int32_t));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd11_freebsd32_getdents(struct thread *td,
|
|
|
|
struct freebsd11_freebsd32_getdents_args *uap)
|
|
|
|
{
|
|
|
|
struct freebsd11_freebsd32_getdirentries_args ap;
|
|
|
|
|
|
|
|
ap.fd = uap->fd;
|
|
|
|
ap.buf = uap->buf;
|
|
|
|
ap.count = uap->count;
|
|
|
|
ap.basep = NULL;
|
|
|
|
return (freebsd11_freebsd32_getdirentries(td, &ap));
|
|
|
|
}
|
|
|
|
#endif /* COMPAT_FREEBSD11 */
|
|
|
|
|
2007-07-04 23:04:41 +00:00
|
|
|
#ifdef COMPAT_FREEBSD6
|
|
|
|
/* versions with the 'int pad' argument */
|
|
|
|
int
|
|
|
|
freebsd6_freebsd32_pread(struct thread *td, struct freebsd6_freebsd32_pread_args *uap)
|
|
|
|
{
|
|
|
|
|
2017-01-31 15:35:18 +00:00
|
|
|
return (kern_pread(td, uap->fd, uap->buf, uap->nbyte,
|
|
|
|
PAIR32TO64(off_t, uap->offset)));
|
2007-07-04 23:04:41 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd6_freebsd32_pwrite(struct thread *td, struct freebsd6_freebsd32_pwrite_args *uap)
|
|
|
|
{
|
|
|
|
|
2017-01-31 15:35:18 +00:00
|
|
|
return (kern_pwrite(td, uap->fd, uap->buf, uap->nbyte,
|
|
|
|
PAIR32TO64(off_t, uap->offset)));
|
2007-07-04 23:04:41 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd6_freebsd32_lseek(struct thread *td, struct freebsd6_freebsd32_lseek_args *uap)
|
|
|
|
{
|
|
|
|
int error;
|
|
|
|
off_t pos;
|
|
|
|
|
2017-01-30 12:24:47 +00:00
|
|
|
error = kern_lseek(td, uap->fd, PAIR32TO64(off_t, uap->offset),
|
|
|
|
uap->whence);
|
2007-07-04 23:04:41 +00:00
|
|
|
/* Expand the quad return into two parts for eax and edx */
|
|
|
|
pos = *(off_t *)(td->td_retval);
|
2010-03-11 14:49:06 +00:00
|
|
|
td->td_retval[RETVAL_LO] = pos & 0xffffffff; /* %eax */
|
|
|
|
td->td_retval[RETVAL_HI] = pos >> 32; /* %edx */
|
2007-07-04 23:04:41 +00:00
|
|
|
return error;
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd6_freebsd32_truncate(struct thread *td, struct freebsd6_freebsd32_truncate_args *uap)
|
|
|
|
{
|
|
|
|
|
2017-01-31 15:19:44 +00:00
|
|
|
return (kern_truncate(td, uap->path, UIO_USERSPACE,
|
|
|
|
PAIR32TO64(off_t, uap->length)));
|
2007-07-04 23:04:41 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd6_freebsd32_ftruncate(struct thread *td, struct freebsd6_freebsd32_ftruncate_args *uap)
|
|
|
|
{
|
|
|
|
|
2017-01-30 11:50:54 +00:00
|
|
|
return (kern_ftruncate(td, uap->fd, PAIR32TO64(off_t, uap->length)));
|
2007-07-04 23:04:41 +00:00
|
|
|
}
|
|
|
|
#endif /* COMPAT_FREEBSD6 */
|
|
|
|
|
2006-02-28 19:39:18 +00:00
|
|
|
struct sf_hdtr32 {
|
|
|
|
uint32_t headers;
|
|
|
|
int hdr_cnt;
|
|
|
|
uint32_t trailers;
|
|
|
|
int trl_cnt;
|
|
|
|
};
|
|
|
|
|
|
|
|
static int
|
|
|
|
freebsd32_do_sendfile(struct thread *td,
|
|
|
|
struct freebsd32_sendfile_args *uap, int compat)
|
2002-10-09 22:27:24 +00:00
|
|
|
{
|
2006-02-28 19:39:18 +00:00
|
|
|
struct sf_hdtr32 hdtr32;
|
|
|
|
struct sf_hdtr hdtr;
|
|
|
|
struct uio *hdr_uio, *trl_uio;
|
2014-11-11 22:08:18 +00:00
|
|
|
struct file *fp;
|
|
|
|
cap_rights_t rights;
|
2006-02-28 19:39:18 +00:00
|
|
|
struct iovec32 *iov32;
|
2014-11-11 20:32:46 +00:00
|
|
|
off_t offset, sbytes;
|
2006-02-28 19:39:18 +00:00
|
|
|
int error;
|
|
|
|
|
2013-08-15 07:54:31 +00:00
|
|
|
offset = PAIR32TO64(off_t, uap->offset);
|
|
|
|
if (offset < 0)
|
|
|
|
return (EINVAL);
|
2002-10-09 22:27:24 +00:00
|
|
|
|
2013-08-15 07:54:31 +00:00
|
|
|
hdr_uio = trl_uio = NULL;
|
2006-02-28 19:39:18 +00:00
|
|
|
|
|
|
|
if (uap->hdtr != NULL) {
|
|
|
|
error = copyin(uap->hdtr, &hdtr32, sizeof(hdtr32));
|
|
|
|
if (error)
|
|
|
|
goto out;
|
|
|
|
PTRIN_CP(hdtr32, hdtr, headers);
|
|
|
|
CP(hdtr32, hdtr, hdr_cnt);
|
|
|
|
PTRIN_CP(hdtr32, hdtr, trailers);
|
|
|
|
CP(hdtr32, hdtr, trl_cnt);
|
|
|
|
|
|
|
|
if (hdtr.headers != NULL) {
|
2006-07-10 19:37:43 +00:00
|
|
|
iov32 = PTRIN(hdtr32.headers);
|
2006-02-28 19:39:18 +00:00
|
|
|
error = freebsd32_copyinuio(iov32,
|
|
|
|
hdtr32.hdr_cnt, &hdr_uio);
|
|
|
|
if (error)
|
|
|
|
goto out;
|
The sendfile(2) allows to send extra data from userspace before the file
data (headers). Historically the size of the headers was not checked
against the socket buffer space. Application could easily overcommit the
socket buffer space.
With the new sendfile (r293439) the problem remained, but a KASSERT was
inserted that checked that amount of data written to the socket matches
its space. In case when size of headers is bigger that socket space,
KASSERT fires. Without INVARIANTS the new sendfile won't panic, but
would report incorrect amount of bytes sent.
o With this change, the headers copyin is moved down into the cycle, after
the sbspace() check. The uio size is trimmed by socket space there,
which fixes the overcommit problem and its consequences.
o The compatibility handling for FreeBSD 4 sendfile headers API is pushed
up the stack to syscall wrappers. This required a copy and paste of the
code, but in turn this allowed to remove extra stack carried parameter
from fo_sendfile_t, and embrace entire compat code into #ifdef. If in
future we got more fo_sendfile_t function, the copy and paste level would
even reduce.
Reviewed by: emax, gallatin, Maxim Dounin <mdounin mdounin.ru>
Tested by: Vitalij Satanivskij <satan ukr.net>
Sponsored by: Netflix
2016-03-29 19:57:11 +00:00
|
|
|
#ifdef COMPAT_FREEBSD4
|
|
|
|
/*
|
|
|
|
* In FreeBSD < 5.0 the nbytes to send also included
|
|
|
|
* the header. If compat is specified subtract the
|
|
|
|
* header size from nbytes.
|
|
|
|
*/
|
|
|
|
if (compat) {
|
|
|
|
if (uap->nbytes > hdr_uio->uio_resid)
|
|
|
|
uap->nbytes -= hdr_uio->uio_resid;
|
|
|
|
else
|
|
|
|
uap->nbytes = 0;
|
|
|
|
}
|
|
|
|
#endif
|
2006-02-28 19:39:18 +00:00
|
|
|
}
|
|
|
|
if (hdtr.trailers != NULL) {
|
2006-07-10 19:37:43 +00:00
|
|
|
iov32 = PTRIN(hdtr32.trailers);
|
2006-02-28 19:39:18 +00:00
|
|
|
error = freebsd32_copyinuio(iov32,
|
|
|
|
hdtr32.trl_cnt, &trl_uio);
|
|
|
|
if (error)
|
|
|
|
goto out;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-11-11 20:32:46 +00:00
|
|
|
AUDIT_ARG_FD(uap->fd);
|
|
|
|
|
|
|
|
if ((error = fget_read(td, uap->fd,
|
|
|
|
cap_rights_init(&rights, CAP_PREAD), &fp)) != 0)
|
|
|
|
goto out;
|
2014-01-17 05:26:55 +00:00
|
|
|
|
2014-11-11 20:32:46 +00:00
|
|
|
error = fo_sendfile(fp, uap->s, hdr_uio, trl_uio, offset,
|
The sendfile(2) allows to send extra data from userspace before the file
data (headers). Historically the size of the headers was not checked
against the socket buffer space. Application could easily overcommit the
socket buffer space.
With the new sendfile (r293439) the problem remained, but a KASSERT was
inserted that checked that amount of data written to the socket matches
its space. In case when size of headers is bigger that socket space,
KASSERT fires. Without INVARIANTS the new sendfile won't panic, but
would report incorrect amount of bytes sent.
o With this change, the headers copyin is moved down into the cycle, after
the sbspace() check. The uio size is trimmed by socket space there,
which fixes the overcommit problem and its consequences.
o The compatibility handling for FreeBSD 4 sendfile headers API is pushed
up the stack to syscall wrappers. This required a copy and paste of the
code, but in turn this allowed to remove extra stack carried parameter
from fo_sendfile_t, and embrace entire compat code into #ifdef. If in
future we got more fo_sendfile_t function, the copy and paste level would
even reduce.
Reviewed by: emax, gallatin, Maxim Dounin <mdounin mdounin.ru>
Tested by: Vitalij Satanivskij <satan ukr.net>
Sponsored by: Netflix
2016-03-29 19:57:11 +00:00
|
|
|
uap->nbytes, &sbytes, uap->flags, td);
|
2014-11-11 20:32:46 +00:00
|
|
|
fdrop(fp, td);
|
2013-08-15 07:54:31 +00:00
|
|
|
|
2013-11-26 08:32:37 +00:00
|
|
|
if (uap->sbytes != NULL)
|
|
|
|
copyout(&sbytes, uap->sbytes, sizeof(off_t));
|
2013-08-15 07:54:31 +00:00
|
|
|
|
2006-02-28 19:39:18 +00:00
|
|
|
out:
|
|
|
|
if (hdr_uio)
|
|
|
|
free(hdr_uio, M_IOV);
|
|
|
|
if (trl_uio)
|
|
|
|
free(trl_uio, M_IOV);
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
#ifdef COMPAT_FREEBSD4
|
|
|
|
int
|
|
|
|
freebsd4_freebsd32_sendfile(struct thread *td,
|
|
|
|
struct freebsd4_freebsd32_sendfile_args *uap)
|
|
|
|
{
|
|
|
|
return (freebsd32_do_sendfile(td,
|
|
|
|
(struct freebsd32_sendfile_args *)uap, 1));
|
2002-10-09 22:27:24 +00:00
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_sendfile(struct thread *td, struct freebsd32_sendfile_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
|
|
|
|
2006-02-28 19:39:18 +00:00
|
|
|
return (freebsd32_do_sendfile(td, uap, 0));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
2010-08-04 14:35:05 +00:00
|
|
|
copy_stat(struct stat *in, struct stat32 *out)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2010-08-04 14:35:05 +00:00
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
CP(*in, *out, st_dev);
|
|
|
|
CP(*in, *out, st_ino);
|
|
|
|
CP(*in, *out, st_mode);
|
|
|
|
CP(*in, *out, st_nlink);
|
|
|
|
CP(*in, *out, st_uid);
|
|
|
|
CP(*in, *out, st_gid);
|
|
|
|
CP(*in, *out, st_rdev);
|
2010-03-28 13:13:22 +00:00
|
|
|
TS_CP(*in, *out, st_atim);
|
|
|
|
TS_CP(*in, *out, st_mtim);
|
|
|
|
TS_CP(*in, *out, st_ctim);
|
2002-07-20 02:56:12 +00:00
|
|
|
CP(*in, *out, st_size);
|
|
|
|
CP(*in, *out, st_blocks);
|
|
|
|
CP(*in, *out, st_blksize);
|
|
|
|
CP(*in, *out, st_flags);
|
|
|
|
CP(*in, *out, st_gen);
|
2010-08-04 14:38:20 +00:00
|
|
|
TS_CP(*in, *out, st_birthtim);
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
out->st_padding0 = 0;
|
|
|
|
out->st_padding1 = 0;
|
|
|
|
#ifdef __STAT32_TIME_T_EXT
|
|
|
|
out->st_atim_ext = 0;
|
|
|
|
out->st_mtim_ext = 0;
|
|
|
|
out->st_ctim_ext = 0;
|
|
|
|
out->st_btim_ext = 0;
|
|
|
|
#endif
|
|
|
|
bzero(out->st_spare, sizeof(out->st_spare));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
2011-04-01 11:16:29 +00:00
|
|
|
#ifdef COMPAT_43
|
|
|
|
static void
|
|
|
|
copy_ostat(struct stat *in, struct ostat32 *out)
|
|
|
|
{
|
|
|
|
|
2018-06-13 08:50:43 +00:00
|
|
|
bzero(out, sizeof(*out));
|
2011-04-01 11:16:29 +00:00
|
|
|
CP(*in, *out, st_dev);
|
|
|
|
CP(*in, *out, st_ino);
|
|
|
|
CP(*in, *out, st_mode);
|
|
|
|
CP(*in, *out, st_nlink);
|
|
|
|
CP(*in, *out, st_uid);
|
|
|
|
CP(*in, *out, st_gid);
|
|
|
|
CP(*in, *out, st_rdev);
|
2018-06-13 08:50:43 +00:00
|
|
|
out->st_size = MIN(in->st_size, INT32_MAX);
|
2011-04-01 11:16:29 +00:00
|
|
|
TS_CP(*in, *out, st_atim);
|
|
|
|
TS_CP(*in, *out, st_mtim);
|
|
|
|
TS_CP(*in, *out, st_ctim);
|
|
|
|
CP(*in, *out, st_blksize);
|
|
|
|
CP(*in, *out, st_blocks);
|
|
|
|
CP(*in, *out, st_flags);
|
|
|
|
CP(*in, *out, st_gen);
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#ifdef COMPAT_43
|
|
|
|
int
|
|
|
|
ofreebsd32_stat(struct thread *td, struct ofreebsd32_stat_args *uap)
|
|
|
|
{
|
|
|
|
struct stat sb;
|
|
|
|
struct ostat32 sb32;
|
|
|
|
int error;
|
|
|
|
|
2014-11-13 18:01:51 +00:00
|
|
|
error = kern_statat(td, 0, AT_FDCWD, uap->path, UIO_USERSPACE,
|
|
|
|
&sb, NULL);
|
2011-04-01 11:16:29 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
copy_ostat(&sb, &sb32);
|
|
|
|
error = copyout(&sb32, uap->ub, sizeof (sb32));
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_fstat(struct thread *td, struct freebsd32_fstat_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2003-12-23 03:20:49 +00:00
|
|
|
struct stat ub;
|
|
|
|
struct stat32 ub32;
|
2002-07-20 02:56:12 +00:00
|
|
|
int error;
|
|
|
|
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
error = kern_fstat(td, uap->fd, &ub);
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
2003-12-23 03:20:49 +00:00
|
|
|
copy_stat(&ub, &ub32);
|
|
|
|
error = copyout(&ub32, uap->ub, sizeof(ub32));
|
2002-07-20 02:56:12 +00:00
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2011-04-01 11:16:29 +00:00
|
|
|
#ifdef COMPAT_43
|
|
|
|
int
|
|
|
|
ofreebsd32_fstat(struct thread *td, struct ofreebsd32_fstat_args *uap)
|
|
|
|
{
|
|
|
|
struct stat ub;
|
|
|
|
struct ostat32 ub32;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = kern_fstat(td, uap->fd, &ub);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
copy_ostat(&ub, &ub32);
|
|
|
|
error = copyout(&ub32, uap->ub, sizeof(ub32));
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2008-03-31 12:08:30 +00:00
|
|
|
int
|
|
|
|
freebsd32_fstatat(struct thread *td, struct freebsd32_fstatat_args *uap)
|
|
|
|
{
|
|
|
|
struct stat ub;
|
|
|
|
struct stat32 ub32;
|
|
|
|
int error;
|
|
|
|
|
2014-11-13 18:01:51 +00:00
|
|
|
error = kern_statat(td, uap->flag, uap->fd, uap->path, UIO_USERSPACE,
|
|
|
|
&ub, NULL);
|
2008-03-31 12:08:30 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
copy_stat(&ub, &ub32);
|
|
|
|
error = copyout(&ub32, uap->buf, sizeof(ub32));
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
#ifdef COMPAT_43
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
ofreebsd32_lstat(struct thread *td, struct ofreebsd32_lstat_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2003-12-23 03:20:49 +00:00
|
|
|
struct stat sb;
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
struct ostat32 sb32;
|
- Add a custom version of exec_copyin_args() to deal with the 32-bit
pointers in argv and envv in userland and use that together with
kern_execve() and exec_free_args() to implement freebsd32_execve()
without using the stackgap.
- Fix freebsd32_adjtime() to call adjtime() rather than utimes(). Still
uses stackgap for now.
- Use kern_setitimer(), kern_getitimer(), kern_select(), kern_utimes(),
kern_statfs(), kern_fstatfs(), kern_fhstatfs(), kern_stat(),
kern_fstat(), and kern_lstat().
Tested by: cokane (amd64)
Silence on: amd64, ia64
2005-02-18 18:56:04 +00:00
|
|
|
int error;
|
2003-12-23 03:20:49 +00:00
|
|
|
|
2014-11-13 18:01:51 +00:00
|
|
|
error = kern_statat(td, AT_SYMLINK_NOFOLLOW, AT_FDCWD, uap->path,
|
|
|
|
UIO_USERSPACE, &sb, NULL);
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
copy_ostat(&sb, &sb32);
|
|
|
|
error = copyout(&sb32, uap->ub, sizeof (sb32));
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_fhstat(struct thread *td, struct freebsd32_fhstat_args *uap)
|
|
|
|
{
|
|
|
|
struct stat sb;
|
|
|
|
struct stat32 sb32;
|
|
|
|
struct fhandle fh;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = copyin(uap->u_fhp, &fh, sizeof(fhandle_t));
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
error = kern_fhstat(td, fh, &sb);
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
2003-12-23 03:20:49 +00:00
|
|
|
copy_stat(&sb, &sb32);
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
error = copyout(&sb32, uap->sb, sizeof (sb32));
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
#if defined(COMPAT_FREEBSD11)
|
2017-06-05 11:40:30 +00:00
|
|
|
extern int ino64_trunc_error;
|
|
|
|
|
|
|
|
static int
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
freebsd11_cvtstat32(struct stat *in, struct freebsd11_stat32 *out)
|
|
|
|
{
|
|
|
|
|
|
|
|
CP(*in, *out, st_ino);
|
2017-06-09 11:17:08 +00:00
|
|
|
if (in->st_ino != out->st_ino) {
|
|
|
|
switch (ino64_trunc_error) {
|
|
|
|
default:
|
|
|
|
case 0:
|
|
|
|
break;
|
|
|
|
case 1:
|
|
|
|
return (EOVERFLOW);
|
|
|
|
case 2:
|
|
|
|
out->st_ino = UINT32_MAX;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
CP(*in, *out, st_nlink);
|
2017-06-09 11:17:08 +00:00
|
|
|
if (in->st_nlink != out->st_nlink) {
|
|
|
|
switch (ino64_trunc_error) {
|
|
|
|
default:
|
|
|
|
case 0:
|
|
|
|
break;
|
|
|
|
case 1:
|
|
|
|
return (EOVERFLOW);
|
|
|
|
case 2:
|
|
|
|
out->st_nlink = UINT16_MAX;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
Fix the encoding of major and minor numbers in 64-bit dev_t by restoring
the old encodings for the lower 16 and 32 bits and only using the
higher 32 bits for unusually large major and minor numbers. This
change breaks compatibility with the previous encoding (which was only
used in -current).
Fix truncation to (essentially) 16-bit dev_t in newnfs v3.
Any encoding of device numbers gives an ABI, so it can't be changed
without translations for compatibility. Extra bits give the much
larger complication that the translations need to compress into fewer
bits. Fortunately, more than 32 bits are rarely needed, so
compression is rarely needed except for 16-bit linux dev_t where it
was always needed but never done.
The previous encoding moved the major number into the top 32 bits.
Almost no translation code handled this, so the major number was blindly
truncated away in most 32-bit encodings. E.g., for ffs, mknod(8) with
major = 1 and minor = 2 gave dev_t = 0x10000002; ffs cannot represent
this and blindly truncated it to 2. But if this mknod was run on any
released version of FreeBSD, it gives dev_t = 0x102. ffs can represent
this, but in the previous encoding it was not decoded, giving major = 0,
minor = 0x102.
The presence of bugs was most obvious for exporting dev_t's from an
old system to -current, since bugs in newnfs augment them. I fixed
oldnfs to support 32-bit dev_t in 1996 (r16634), but this regressed
to 16-bit dev_t in newnfs, first to the old 16-bit encoding and then
further in -current. E.g., old ad0 with major = 234, minor = 0x10002
had the correct (major, minor) number on the wire, but newnfs truncated
this to (234, 2) and then the previous encoding shifted the major
number into oblivion as seen by ffs or old applications.
I first tried to fix this by translating on every ABI/API boundary, but
there are too many boundaries and too many sloppy translations by blind
truncation. So use the old encoding for the low 32 bits so that sloppy
translations work no worse than before provided the high 32 bits are
not set. Add some error checking for when bits are lost. Keep not
doing any error checking for translations for almost everything in
compat/linux.
compat/freebsd32/freebsd32_misc.c:
Optionally check for losing bits after possibly-truncating assignments as
before.
compat/linux/linux_stats.c:
Depend on the representation being compatible with Linux's (or just with
itself for local use) and spell some of the translations as assignments in
a macro that hides the details.
fs/nfsclient/nfs_clcomsubs.c:
Essentially the same fix as in 1996, except there is now no possible
truncation in makedev() itself. Also fix nearby style bugs.
kern/vfs_syscalls.c:
As for freebsd32. Also update the sysctl description to include file
numbers, and change it to describe device ids as device numbers.
sys/types.h:
Use inline functions (wrapped by macros) since the expressions are now
a bit too complicated for plain macros. Describe the encoding and
some of the reasons for it. 16-bit compatibility didn't leave many
reasonable choices for the 32-bit encoding, and 32-bit compatibility
doesn't leave many reasonable choices for the 64-bit encoding. My
choice is to put the 8 new minor bits in the low 8 bits of the top 32
bits. This minimizes discontiguities.
Reviewed by: kib (except for rewrite of the comment in linux_stats.c)
2018-06-13 12:22:00 +00:00
|
|
|
out->st_dev = in->st_dev;
|
|
|
|
if (out->st_dev != in->st_dev) {
|
|
|
|
switch (ino64_trunc_error) {
|
|
|
|
default:
|
|
|
|
break;
|
|
|
|
case 1:
|
|
|
|
return (EOVERFLOW);
|
|
|
|
}
|
|
|
|
}
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
CP(*in, *out, st_mode);
|
|
|
|
CP(*in, *out, st_uid);
|
|
|
|
CP(*in, *out, st_gid);
|
Fix the encoding of major and minor numbers in 64-bit dev_t by restoring
the old encodings for the lower 16 and 32 bits and only using the
higher 32 bits for unusually large major and minor numbers. This
change breaks compatibility with the previous encoding (which was only
used in -current).
Fix truncation to (essentially) 16-bit dev_t in newnfs v3.
Any encoding of device numbers gives an ABI, so it can't be changed
without translations for compatibility. Extra bits give the much
larger complication that the translations need to compress into fewer
bits. Fortunately, more than 32 bits are rarely needed, so
compression is rarely needed except for 16-bit linux dev_t where it
was always needed but never done.
The previous encoding moved the major number into the top 32 bits.
Almost no translation code handled this, so the major number was blindly
truncated away in most 32-bit encodings. E.g., for ffs, mknod(8) with
major = 1 and minor = 2 gave dev_t = 0x10000002; ffs cannot represent
this and blindly truncated it to 2. But if this mknod was run on any
released version of FreeBSD, it gives dev_t = 0x102. ffs can represent
this, but in the previous encoding it was not decoded, giving major = 0,
minor = 0x102.
The presence of bugs was most obvious for exporting dev_t's from an
old system to -current, since bugs in newnfs augment them. I fixed
oldnfs to support 32-bit dev_t in 1996 (r16634), but this regressed
to 16-bit dev_t in newnfs, first to the old 16-bit encoding and then
further in -current. E.g., old ad0 with major = 234, minor = 0x10002
had the correct (major, minor) number on the wire, but newnfs truncated
this to (234, 2) and then the previous encoding shifted the major
number into oblivion as seen by ffs or old applications.
I first tried to fix this by translating on every ABI/API boundary, but
there are too many boundaries and too many sloppy translations by blind
truncation. So use the old encoding for the low 32 bits so that sloppy
translations work no worse than before provided the high 32 bits are
not set. Add some error checking for when bits are lost. Keep not
doing any error checking for translations for almost everything in
compat/linux.
compat/freebsd32/freebsd32_misc.c:
Optionally check for losing bits after possibly-truncating assignments as
before.
compat/linux/linux_stats.c:
Depend on the representation being compatible with Linux's (or just with
itself for local use) and spell some of the translations as assignments in
a macro that hides the details.
fs/nfsclient/nfs_clcomsubs.c:
Essentially the same fix as in 1996, except there is now no possible
truncation in makedev() itself. Also fix nearby style bugs.
kern/vfs_syscalls.c:
As for freebsd32. Also update the sysctl description to include file
numbers, and change it to describe device ids as device numbers.
sys/types.h:
Use inline functions (wrapped by macros) since the expressions are now
a bit too complicated for plain macros. Describe the encoding and
some of the reasons for it. 16-bit compatibility didn't leave many
reasonable choices for the 32-bit encoding, and 32-bit compatibility
doesn't leave many reasonable choices for the 64-bit encoding. My
choice is to put the 8 new minor bits in the low 8 bits of the top 32
bits. This minimizes discontiguities.
Reviewed by: kib (except for rewrite of the comment in linux_stats.c)
2018-06-13 12:22:00 +00:00
|
|
|
out->st_rdev = in->st_rdev;
|
|
|
|
if (out->st_rdev != in->st_rdev) {
|
|
|
|
switch (ino64_trunc_error) {
|
|
|
|
default:
|
|
|
|
break;
|
|
|
|
case 1:
|
|
|
|
return (EOVERFLOW);
|
|
|
|
}
|
|
|
|
}
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
TS_CP(*in, *out, st_atim);
|
|
|
|
TS_CP(*in, *out, st_mtim);
|
|
|
|
TS_CP(*in, *out, st_ctim);
|
|
|
|
CP(*in, *out, st_size);
|
|
|
|
CP(*in, *out, st_blocks);
|
|
|
|
CP(*in, *out, st_blksize);
|
|
|
|
CP(*in, *out, st_flags);
|
|
|
|
CP(*in, *out, st_gen);
|
|
|
|
TS_CP(*in, *out, st_birthtim);
|
|
|
|
out->st_lspare = 0;
|
|
|
|
bzero((char *)&out->st_birthtim + sizeof(out->st_birthtim),
|
|
|
|
sizeof(*out) - offsetof(struct freebsd11_stat32,
|
|
|
|
st_birthtim) - sizeof(out->st_birthtim));
|
2017-06-05 11:40:30 +00:00
|
|
|
return (0);
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd11_freebsd32_stat(struct thread *td,
|
|
|
|
struct freebsd11_freebsd32_stat_args *uap)
|
|
|
|
{
|
|
|
|
struct stat sb;
|
|
|
|
struct freebsd11_stat32 sb32;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = kern_statat(td, 0, AT_FDCWD, uap->path, UIO_USERSPACE,
|
|
|
|
&sb, NULL);
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
2017-06-05 11:40:30 +00:00
|
|
|
error = freebsd11_cvtstat32(&sb, &sb32);
|
|
|
|
if (error == 0)
|
|
|
|
error = copyout(&sb32, uap->ub, sizeof (sb32));
|
2002-07-20 02:56:12 +00:00
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2011-04-01 11:16:29 +00:00
|
|
|
int
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
freebsd11_freebsd32_fstat(struct thread *td,
|
|
|
|
struct freebsd11_freebsd32_fstat_args *uap)
|
2011-04-01 11:16:29 +00:00
|
|
|
{
|
|
|
|
struct stat sb;
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
struct freebsd11_stat32 sb32;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = kern_fstat(td, uap->fd, &sb);
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
2017-06-05 11:40:30 +00:00
|
|
|
error = freebsd11_cvtstat32(&sb, &sb32);
|
|
|
|
if (error == 0)
|
|
|
|
error = copyout(&sb32, uap->ub, sizeof (sb32));
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd11_freebsd32_fstatat(struct thread *td,
|
|
|
|
struct freebsd11_freebsd32_fstatat_args *uap)
|
|
|
|
{
|
|
|
|
struct stat sb;
|
|
|
|
struct freebsd11_stat32 sb32;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = kern_statat(td, uap->flag, uap->fd, uap->path, UIO_USERSPACE,
|
|
|
|
&sb, NULL);
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
2017-06-05 11:40:30 +00:00
|
|
|
error = freebsd11_cvtstat32(&sb, &sb32);
|
|
|
|
if (error == 0)
|
|
|
|
error = copyout(&sb32, uap->buf, sizeof (sb32));
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd11_freebsd32_lstat(struct thread *td,
|
|
|
|
struct freebsd11_freebsd32_lstat_args *uap)
|
|
|
|
{
|
|
|
|
struct stat sb;
|
|
|
|
struct freebsd11_stat32 sb32;
|
2011-04-01 11:16:29 +00:00
|
|
|
int error;
|
|
|
|
|
2014-11-13 18:01:51 +00:00
|
|
|
error = kern_statat(td, AT_SYMLINK_NOFOLLOW, AT_FDCWD, uap->path,
|
|
|
|
UIO_USERSPACE, &sb, NULL);
|
2017-06-05 11:40:30 +00:00
|
|
|
if (error != 0)
|
2011-04-01 11:16:29 +00:00
|
|
|
return (error);
|
2017-06-05 11:40:30 +00:00
|
|
|
error = freebsd11_cvtstat32(&sb, &sb32);
|
|
|
|
if (error == 0)
|
|
|
|
error = copyout(&sb32, uap->ub, sizeof (sb32));
|
2011-04-01 11:16:29 +00:00
|
|
|
return (error);
|
|
|
|
}
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
|
|
|
|
int
|
|
|
|
freebsd11_freebsd32_fhstat(struct thread *td,
|
|
|
|
struct freebsd11_freebsd32_fhstat_args *uap)
|
|
|
|
{
|
|
|
|
struct stat sb;
|
|
|
|
struct freebsd11_stat32 sb32;
|
|
|
|
struct fhandle fh;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = copyin(uap->u_fhp, &fh, sizeof(fhandle_t));
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
error = kern_fhstat(td, fh, &sb);
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
2017-06-05 11:40:30 +00:00
|
|
|
error = freebsd11_cvtstat32(&sb, &sb32);
|
|
|
|
if (error == 0)
|
|
|
|
error = copyout(&sb32, uap->sb, sizeof (sb32));
|
Commit the 64-bit inode project.
Extend the ino_t, dev_t, nlink_t types to 64-bit ints. Modify
struct dirent layout to add d_off, increase the size of d_fileno
to 64-bits, increase the size of d_namlen to 16-bits, and change
the required alignment. Increase struct statfs f_mntfromname[] and
f_mntonname[] array length MNAMELEN to 1024.
ABI breakage is mitigated by providing compatibility using versioned
symbols, ingenious use of the existing padding in structures, and
by employing other tricks. Unfortunately, not everything can be
fixed, especially outside the base system. For instance, third-party
APIs which pass struct stat around are broken in backward and
forward incompatible ways.
Kinfo sysctl MIBs ABI is changed in backward-compatible way, but
there is no general mechanism to handle other sysctl MIBS which
return structures where the layout has changed. It was considered
that the breakage is either in the management interfaces, where we
usually allow ABI slip, or is not important.
Struct xvnode changed layout, no compat shims are provided.
For struct xtty, dev_t tty device member was reduced to uint32_t.
It was decided that keeping ABI compat in this case is more useful
than reporting 64-bit dev_t, for the sake of pstat.
Update note: strictly follow the instructions in UPDATING. Build
and install the new kernel with COMPAT_FREEBSD11 option enabled,
then reboot, and only then install new world.
Credits: The 64-bit inode project, also known as ino64, started life
many years ago as a project by Gleb Kurtsou (gleb). Kirk McKusick
(mckusick) then picked up and updated the patch, and acted as a
flag-waver. Feedback, suggestions, and discussions were carried
by Ed Maste (emaste), John Baldwin (jhb), Jilles Tjoelker (jilles),
and Rick Macklem (rmacklem). Kris Moore (kris) performed an initial
ports investigation followed by an exp-run by Antoine Brodin (antoine).
Essential and all-embracing testing was done by Peter Holm (pho).
The heavy lifting of coordinating all these efforts and bringing the
project to completion were done by Konstantin Belousov (kib).
Sponsored by: The FreeBSD Foundation (emaste, kib)
Differential revision: https://reviews.freebsd.org/D10439
2017-05-23 09:29:05 +00:00
|
|
|
return (error);
|
|
|
|
}
|
2011-04-01 11:16:29 +00:00
|
|
|
#endif
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2018-11-09 00:21:58 +00:00
|
|
|
freebsd32___sysctl(struct thread *td, struct freebsd32___sysctl_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
|
|
|
int error, name[CTL_MAXNAME];
|
|
|
|
size_t j, oldlen;
|
2014-10-28 15:28:20 +00:00
|
|
|
uint32_t tmp;
|
2002-07-20 02:56:12 +00:00
|
|
|
|
|
|
|
if (uap->namelen > CTL_MAXNAME || uap->namelen < 2)
|
|
|
|
return (EINVAL);
|
2004-10-11 22:04:16 +00:00
|
|
|
error = copyin(uap->name, name, uap->namelen * sizeof(int));
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
2014-10-28 15:28:20 +00:00
|
|
|
if (uap->oldlenp) {
|
|
|
|
error = fueword32(uap->oldlenp, &tmp);
|
|
|
|
oldlen = tmp;
|
|
|
|
} else {
|
2002-07-20 02:56:12 +00:00
|
|
|
oldlen = 0;
|
2014-10-28 15:28:20 +00:00
|
|
|
}
|
|
|
|
if (error != 0)
|
|
|
|
return (EFAULT);
|
2002-07-20 02:56:12 +00:00
|
|
|
error = userland_sysctl(td, name, uap->namelen,
|
|
|
|
uap->old, &oldlen, 1,
|
2004-10-11 22:04:16 +00:00
|
|
|
uap->new, uap->newlen, &j, SCTL_MASK32);
|
2018-05-15 16:24:58 +00:00
|
|
|
if (error)
|
2008-12-29 12:58:45 +00:00
|
|
|
return (error);
|
2004-10-11 22:04:16 +00:00
|
|
|
if (uap->oldlenp)
|
2002-07-20 02:56:12 +00:00
|
|
|
suword32(uap->oldlenp, j);
|
2008-12-29 12:58:45 +00:00
|
|
|
return (0);
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
|
2019-09-03 04:16:30 +00:00
|
|
|
int
|
|
|
|
freebsd32___sysctlbyname(struct thread *td,
|
|
|
|
struct freebsd32___sysctlbyname_args *uap)
|
|
|
|
{
|
|
|
|
size_t oldlen, rv;
|
|
|
|
int error;
|
|
|
|
uint32_t tmp;
|
|
|
|
|
|
|
|
if (uap->oldlenp != NULL) {
|
|
|
|
error = fueword32(uap->oldlenp, &tmp);
|
|
|
|
oldlen = tmp;
|
|
|
|
} else {
|
|
|
|
error = oldlen = 0;
|
|
|
|
}
|
|
|
|
if (error != 0)
|
|
|
|
return (EFAULT);
|
|
|
|
error = kern___sysctlbyname(td, uap->name, uap->namelen, uap->old,
|
|
|
|
&oldlen, uap->new, uap->newlen, &rv, SCTL_MASK32, 1);
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
if (uap->oldlenp != NULL)
|
|
|
|
error = suword32(uap->oldlenp, rv);
|
|
|
|
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
MFp4:
Bring in updated jail support from bz_jail branch.
This enhances the current jail implementation to permit multiple
addresses per jail. In addtion to IPv4, IPv6 is supported as well.
Due to updated checks it is even possible to have jails without
an IP address at all, which basically gives one a chroot with
restricted process view, no networking,..
SCTP support was updated and supports IPv6 in jails as well.
Cpuset support permits jails to be bound to specific processor
sets after creation.
Jails can have an unrestricted (no duplicate protection, etc.) name
in addition to the hostname. The jail name cannot be changed from
within a jail and is considered to be used for management purposes
or as audit-token in the future.
DDB 'show jails' command was added to aid debugging.
Proper compat support permits 32bit jail binaries to be used on 64bit
systems to manage jails. Also backward compatibility was preserved where
possible: for jail v1 syscalls, as well as with user space management
utilities.
Both jail as well as prison version were updated for the new features.
A gap was intentionally left as the intermediate versions had been
used by various patches floating around the last years.
Bump __FreeBSD_version for the afore mentioned and in kernel changes.
Special thanks to:
- Pawel Jakub Dawidek (pjd) for his multi-IPv4 patches
and Olivier Houchard (cognet) for initial single-IPv6 patches.
- Jeff Roberson (jeff) and Randall Stewart (rrs) for their
help, ideas and review on cpuset and SCTP support.
- Robert Watson (rwatson) for lots and lots of help, discussions,
suggestions and review of most of the patch at various stages.
- John Baldwin (jhb) for his help.
- Simon L. Nielsen (simon) as early adopter testing changes
on cluster machines as well as all the testers and people
who provided feedback the last months on freebsd-jail and
other channels.
- My employer, CK Software GmbH, for the support so I could work on this.
Reviewed by: (see above)
MFC after: 3 months (this is just so that I get the mail)
X-MFC Before: 7.2-RELEASE if possible
2008-11-29 14:32:14 +00:00
|
|
|
int
|
2018-08-16 19:09:43 +00:00
|
|
|
freebsd32_jail(struct thread *td, struct freebsd32_jail_args *uap)
|
MFp4:
Bring in updated jail support from bz_jail branch.
This enhances the current jail implementation to permit multiple
addresses per jail. In addtion to IPv4, IPv6 is supported as well.
Due to updated checks it is even possible to have jails without
an IP address at all, which basically gives one a chroot with
restricted process view, no networking,..
SCTP support was updated and supports IPv6 in jails as well.
Cpuset support permits jails to be bound to specific processor
sets after creation.
Jails can have an unrestricted (no duplicate protection, etc.) name
in addition to the hostname. The jail name cannot be changed from
within a jail and is considered to be used for management purposes
or as audit-token in the future.
DDB 'show jails' command was added to aid debugging.
Proper compat support permits 32bit jail binaries to be used on 64bit
systems to manage jails. Also backward compatibility was preserved where
possible: for jail v1 syscalls, as well as with user space management
utilities.
Both jail as well as prison version were updated for the new features.
A gap was intentionally left as the intermediate versions had been
used by various patches floating around the last years.
Bump __FreeBSD_version for the afore mentioned and in kernel changes.
Special thanks to:
- Pawel Jakub Dawidek (pjd) for his multi-IPv4 patches
and Olivier Houchard (cognet) for initial single-IPv6 patches.
- Jeff Roberson (jeff) and Randall Stewart (rrs) for their
help, ideas and review on cpuset and SCTP support.
- Robert Watson (rwatson) for lots and lots of help, discussions,
suggestions and review of most of the patch at various stages.
- John Baldwin (jhb) for his help.
- Simon L. Nielsen (simon) as early adopter testing changes
on cluster machines as well as all the testers and people
who provided feedback the last months on freebsd-jail and
other channels.
- My employer, CK Software GmbH, for the support so I could work on this.
Reviewed by: (see above)
MFC after: 3 months (this is just so that I get the mail)
X-MFC Before: 7.2-RELEASE if possible
2008-11-29 14:32:14 +00:00
|
|
|
{
|
|
|
|
uint32_t version;
|
|
|
|
int error;
|
2009-05-27 14:11:23 +00:00
|
|
|
struct jail j;
|
MFp4:
Bring in updated jail support from bz_jail branch.
This enhances the current jail implementation to permit multiple
addresses per jail. In addtion to IPv4, IPv6 is supported as well.
Due to updated checks it is even possible to have jails without
an IP address at all, which basically gives one a chroot with
restricted process view, no networking,..
SCTP support was updated and supports IPv6 in jails as well.
Cpuset support permits jails to be bound to specific processor
sets after creation.
Jails can have an unrestricted (no duplicate protection, etc.) name
in addition to the hostname. The jail name cannot be changed from
within a jail and is considered to be used for management purposes
or as audit-token in the future.
DDB 'show jails' command was added to aid debugging.
Proper compat support permits 32bit jail binaries to be used on 64bit
systems to manage jails. Also backward compatibility was preserved where
possible: for jail v1 syscalls, as well as with user space management
utilities.
Both jail as well as prison version were updated for the new features.
A gap was intentionally left as the intermediate versions had been
used by various patches floating around the last years.
Bump __FreeBSD_version for the afore mentioned and in kernel changes.
Special thanks to:
- Pawel Jakub Dawidek (pjd) for his multi-IPv4 patches
and Olivier Houchard (cognet) for initial single-IPv6 patches.
- Jeff Roberson (jeff) and Randall Stewart (rrs) for their
help, ideas and review on cpuset and SCTP support.
- Robert Watson (rwatson) for lots and lots of help, discussions,
suggestions and review of most of the patch at various stages.
- John Baldwin (jhb) for his help.
- Simon L. Nielsen (simon) as early adopter testing changes
on cluster machines as well as all the testers and people
who provided feedback the last months on freebsd-jail and
other channels.
- My employer, CK Software GmbH, for the support so I could work on this.
Reviewed by: (see above)
MFC after: 3 months (this is just so that I get the mail)
X-MFC Before: 7.2-RELEASE if possible
2008-11-29 14:32:14 +00:00
|
|
|
|
|
|
|
error = copyin(uap->jail, &version, sizeof(uint32_t));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
2009-03-27 13:13:59 +00:00
|
|
|
|
MFp4:
Bring in updated jail support from bz_jail branch.
This enhances the current jail implementation to permit multiple
addresses per jail. In addtion to IPv4, IPv6 is supported as well.
Due to updated checks it is even possible to have jails without
an IP address at all, which basically gives one a chroot with
restricted process view, no networking,..
SCTP support was updated and supports IPv6 in jails as well.
Cpuset support permits jails to be bound to specific processor
sets after creation.
Jails can have an unrestricted (no duplicate protection, etc.) name
in addition to the hostname. The jail name cannot be changed from
within a jail and is considered to be used for management purposes
or as audit-token in the future.
DDB 'show jails' command was added to aid debugging.
Proper compat support permits 32bit jail binaries to be used on 64bit
systems to manage jails. Also backward compatibility was preserved where
possible: for jail v1 syscalls, as well as with user space management
utilities.
Both jail as well as prison version were updated for the new features.
A gap was intentionally left as the intermediate versions had been
used by various patches floating around the last years.
Bump __FreeBSD_version for the afore mentioned and in kernel changes.
Special thanks to:
- Pawel Jakub Dawidek (pjd) for his multi-IPv4 patches
and Olivier Houchard (cognet) for initial single-IPv6 patches.
- Jeff Roberson (jeff) and Randall Stewart (rrs) for their
help, ideas and review on cpuset and SCTP support.
- Robert Watson (rwatson) for lots and lots of help, discussions,
suggestions and review of most of the patch at various stages.
- John Baldwin (jhb) for his help.
- Simon L. Nielsen (simon) as early adopter testing changes
on cluster machines as well as all the testers and people
who provided feedback the last months on freebsd-jail and
other channels.
- My employer, CK Software GmbH, for the support so I could work on this.
Reviewed by: (see above)
MFC after: 3 months (this is just so that I get the mail)
X-MFC Before: 7.2-RELEASE if possible
2008-11-29 14:32:14 +00:00
|
|
|
switch (version) {
|
2009-03-27 13:13:59 +00:00
|
|
|
case 0:
|
MFp4:
Bring in updated jail support from bz_jail branch.
This enhances the current jail implementation to permit multiple
addresses per jail. In addtion to IPv4, IPv6 is supported as well.
Due to updated checks it is even possible to have jails without
an IP address at all, which basically gives one a chroot with
restricted process view, no networking,..
SCTP support was updated and supports IPv6 in jails as well.
Cpuset support permits jails to be bound to specific processor
sets after creation.
Jails can have an unrestricted (no duplicate protection, etc.) name
in addition to the hostname. The jail name cannot be changed from
within a jail and is considered to be used for management purposes
or as audit-token in the future.
DDB 'show jails' command was added to aid debugging.
Proper compat support permits 32bit jail binaries to be used on 64bit
systems to manage jails. Also backward compatibility was preserved where
possible: for jail v1 syscalls, as well as with user space management
utilities.
Both jail as well as prison version were updated for the new features.
A gap was intentionally left as the intermediate versions had been
used by various patches floating around the last years.
Bump __FreeBSD_version for the afore mentioned and in kernel changes.
Special thanks to:
- Pawel Jakub Dawidek (pjd) for his multi-IPv4 patches
and Olivier Houchard (cognet) for initial single-IPv6 patches.
- Jeff Roberson (jeff) and Randall Stewart (rrs) for their
help, ideas and review on cpuset and SCTP support.
- Robert Watson (rwatson) for lots and lots of help, discussions,
suggestions and review of most of the patch at various stages.
- John Baldwin (jhb) for his help.
- Simon L. Nielsen (simon) as early adopter testing changes
on cluster machines as well as all the testers and people
who provided feedback the last months on freebsd-jail and
other channels.
- My employer, CK Software GmbH, for the support so I could work on this.
Reviewed by: (see above)
MFC after: 3 months (this is just so that I get the mail)
X-MFC Before: 7.2-RELEASE if possible
2008-11-29 14:32:14 +00:00
|
|
|
{
|
|
|
|
/* FreeBSD single IPv4 jails. */
|
|
|
|
struct jail32_v0 j32_v0;
|
|
|
|
|
2009-05-27 14:11:23 +00:00
|
|
|
bzero(&j, sizeof(struct jail));
|
MFp4:
Bring in updated jail support from bz_jail branch.
This enhances the current jail implementation to permit multiple
addresses per jail. In addtion to IPv4, IPv6 is supported as well.
Due to updated checks it is even possible to have jails without
an IP address at all, which basically gives one a chroot with
restricted process view, no networking,..
SCTP support was updated and supports IPv6 in jails as well.
Cpuset support permits jails to be bound to specific processor
sets after creation.
Jails can have an unrestricted (no duplicate protection, etc.) name
in addition to the hostname. The jail name cannot be changed from
within a jail and is considered to be used for management purposes
or as audit-token in the future.
DDB 'show jails' command was added to aid debugging.
Proper compat support permits 32bit jail binaries to be used on 64bit
systems to manage jails. Also backward compatibility was preserved where
possible: for jail v1 syscalls, as well as with user space management
utilities.
Both jail as well as prison version were updated for the new features.
A gap was intentionally left as the intermediate versions had been
used by various patches floating around the last years.
Bump __FreeBSD_version for the afore mentioned and in kernel changes.
Special thanks to:
- Pawel Jakub Dawidek (pjd) for his multi-IPv4 patches
and Olivier Houchard (cognet) for initial single-IPv6 patches.
- Jeff Roberson (jeff) and Randall Stewart (rrs) for their
help, ideas and review on cpuset and SCTP support.
- Robert Watson (rwatson) for lots and lots of help, discussions,
suggestions and review of most of the patch at various stages.
- John Baldwin (jhb) for his help.
- Simon L. Nielsen (simon) as early adopter testing changes
on cluster machines as well as all the testers and people
who provided feedback the last months on freebsd-jail and
other channels.
- My employer, CK Software GmbH, for the support so I could work on this.
Reviewed by: (see above)
MFC after: 3 months (this is just so that I get the mail)
X-MFC Before: 7.2-RELEASE if possible
2008-11-29 14:32:14 +00:00
|
|
|
error = copyin(uap->jail, &j32_v0, sizeof(struct jail32_v0));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
2009-05-27 14:11:23 +00:00
|
|
|
CP(j32_v0, j, version);
|
|
|
|
PTRIN_CP(j32_v0, j, path);
|
|
|
|
PTRIN_CP(j32_v0, j, hostname);
|
2013-11-28 19:40:33 +00:00
|
|
|
j.ip4s = htonl(j32_v0.ip_number); /* jail_v0 is host order */
|
MFp4:
Bring in updated jail support from bz_jail branch.
This enhances the current jail implementation to permit multiple
addresses per jail. In addtion to IPv4, IPv6 is supported as well.
Due to updated checks it is even possible to have jails without
an IP address at all, which basically gives one a chroot with
restricted process view, no networking,..
SCTP support was updated and supports IPv6 in jails as well.
Cpuset support permits jails to be bound to specific processor
sets after creation.
Jails can have an unrestricted (no duplicate protection, etc.) name
in addition to the hostname. The jail name cannot be changed from
within a jail and is considered to be used for management purposes
or as audit-token in the future.
DDB 'show jails' command was added to aid debugging.
Proper compat support permits 32bit jail binaries to be used on 64bit
systems to manage jails. Also backward compatibility was preserved where
possible: for jail v1 syscalls, as well as with user space management
utilities.
Both jail as well as prison version were updated for the new features.
A gap was intentionally left as the intermediate versions had been
used by various patches floating around the last years.
Bump __FreeBSD_version for the afore mentioned and in kernel changes.
Special thanks to:
- Pawel Jakub Dawidek (pjd) for his multi-IPv4 patches
and Olivier Houchard (cognet) for initial single-IPv6 patches.
- Jeff Roberson (jeff) and Randall Stewart (rrs) for their
help, ideas and review on cpuset and SCTP support.
- Robert Watson (rwatson) for lots and lots of help, discussions,
suggestions and review of most of the patch at various stages.
- John Baldwin (jhb) for his help.
- Simon L. Nielsen (simon) as early adopter testing changes
on cluster machines as well as all the testers and people
who provided feedback the last months on freebsd-jail and
other channels.
- My employer, CK Software GmbH, for the support so I could work on this.
Reviewed by: (see above)
MFC after: 3 months (this is just so that I get the mail)
X-MFC Before: 7.2-RELEASE if possible
2008-11-29 14:32:14 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
case 1:
|
|
|
|
/*
|
|
|
|
* Version 1 was used by multi-IPv4 jail implementations
|
|
|
|
* that never made it into the official kernel.
|
|
|
|
*/
|
|
|
|
return (EINVAL);
|
|
|
|
|
|
|
|
case 2: /* JAIL_API_VERSION */
|
|
|
|
{
|
|
|
|
/* FreeBSD multi-IPv4/IPv6,noIP jails. */
|
|
|
|
struct jail32 j32;
|
|
|
|
|
|
|
|
error = copyin(uap->jail, &j32, sizeof(struct jail32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
2009-05-27 14:11:23 +00:00
|
|
|
CP(j32, j, version);
|
|
|
|
PTRIN_CP(j32, j, path);
|
|
|
|
PTRIN_CP(j32, j, hostname);
|
|
|
|
PTRIN_CP(j32, j, jailname);
|
|
|
|
CP(j32, j, ip4s);
|
|
|
|
CP(j32, j, ip6s);
|
|
|
|
PTRIN_CP(j32, j, ip4);
|
|
|
|
PTRIN_CP(j32, j, ip6);
|
MFp4:
Bring in updated jail support from bz_jail branch.
This enhances the current jail implementation to permit multiple
addresses per jail. In addtion to IPv4, IPv6 is supported as well.
Due to updated checks it is even possible to have jails without
an IP address at all, which basically gives one a chroot with
restricted process view, no networking,..
SCTP support was updated and supports IPv6 in jails as well.
Cpuset support permits jails to be bound to specific processor
sets after creation.
Jails can have an unrestricted (no duplicate protection, etc.) name
in addition to the hostname. The jail name cannot be changed from
within a jail and is considered to be used for management purposes
or as audit-token in the future.
DDB 'show jails' command was added to aid debugging.
Proper compat support permits 32bit jail binaries to be used on 64bit
systems to manage jails. Also backward compatibility was preserved where
possible: for jail v1 syscalls, as well as with user space management
utilities.
Both jail as well as prison version were updated for the new features.
A gap was intentionally left as the intermediate versions had been
used by various patches floating around the last years.
Bump __FreeBSD_version for the afore mentioned and in kernel changes.
Special thanks to:
- Pawel Jakub Dawidek (pjd) for his multi-IPv4 patches
and Olivier Houchard (cognet) for initial single-IPv6 patches.
- Jeff Roberson (jeff) and Randall Stewart (rrs) for their
help, ideas and review on cpuset and SCTP support.
- Robert Watson (rwatson) for lots and lots of help, discussions,
suggestions and review of most of the patch at various stages.
- John Baldwin (jhb) for his help.
- Simon L. Nielsen (simon) as early adopter testing changes
on cluster machines as well as all the testers and people
who provided feedback the last months on freebsd-jail and
other channels.
- My employer, CK Software GmbH, for the support so I could work on this.
Reviewed by: (see above)
MFC after: 3 months (this is just so that I get the mail)
X-MFC Before: 7.2-RELEASE if possible
2008-11-29 14:32:14 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
default:
|
|
|
|
/* Sci-Fi jails are not supported, sorry. */
|
|
|
|
return (EINVAL);
|
|
|
|
}
|
2018-08-16 19:09:43 +00:00
|
|
|
return (kern_jail(td, &j));
|
2009-04-29 21:14:15 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_jail_set(struct thread *td, struct freebsd32_jail_set_args *uap)
|
|
|
|
{
|
|
|
|
struct uio *auio;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
/* Check that we have an even number of iovecs. */
|
|
|
|
if (uap->iovcnt & 1)
|
|
|
|
return (EINVAL);
|
|
|
|
|
|
|
|
error = freebsd32_copyinuio(uap->iovp, uap->iovcnt, &auio);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
error = kern_jail_set(td, auio, uap->flags);
|
|
|
|
free(auio, M_IOV);
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_jail_get(struct thread *td, struct freebsd32_jail_get_args *uap)
|
|
|
|
{
|
|
|
|
struct iovec32 iov32;
|
|
|
|
struct uio *auio;
|
|
|
|
int error, i;
|
|
|
|
|
|
|
|
/* Check that we have an even number of iovecs. */
|
|
|
|
if (uap->iovcnt & 1)
|
|
|
|
return (EINVAL);
|
|
|
|
|
|
|
|
error = freebsd32_copyinuio(uap->iovp, uap->iovcnt, &auio);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
error = kern_jail_get(td, auio, uap->flags);
|
|
|
|
if (error == 0)
|
|
|
|
for (i = 0; i < uap->iovcnt; i++) {
|
|
|
|
PTROUT_CP(auio->uio_iov[i], iov32, iov_base);
|
|
|
|
CP(auio->uio_iov[i], iov32, iov_len);
|
|
|
|
error = copyout(&iov32, uap->iovp + i, sizeof(iov32));
|
|
|
|
if (error != 0)
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
free(auio, M_IOV);
|
|
|
|
return (error);
|
MFp4:
Bring in updated jail support from bz_jail branch.
This enhances the current jail implementation to permit multiple
addresses per jail. In addtion to IPv4, IPv6 is supported as well.
Due to updated checks it is even possible to have jails without
an IP address at all, which basically gives one a chroot with
restricted process view, no networking,..
SCTP support was updated and supports IPv6 in jails as well.
Cpuset support permits jails to be bound to specific processor
sets after creation.
Jails can have an unrestricted (no duplicate protection, etc.) name
in addition to the hostname. The jail name cannot be changed from
within a jail and is considered to be used for management purposes
or as audit-token in the future.
DDB 'show jails' command was added to aid debugging.
Proper compat support permits 32bit jail binaries to be used on 64bit
systems to manage jails. Also backward compatibility was preserved where
possible: for jail v1 syscalls, as well as with user space management
utilities.
Both jail as well as prison version were updated for the new features.
A gap was intentionally left as the intermediate versions had been
used by various patches floating around the last years.
Bump __FreeBSD_version for the afore mentioned and in kernel changes.
Special thanks to:
- Pawel Jakub Dawidek (pjd) for his multi-IPv4 patches
and Olivier Houchard (cognet) for initial single-IPv6 patches.
- Jeff Roberson (jeff) and Randall Stewart (rrs) for their
help, ideas and review on cpuset and SCTP support.
- Robert Watson (rwatson) for lots and lots of help, discussions,
suggestions and review of most of the patch at various stages.
- John Baldwin (jhb) for his help.
- Simon L. Nielsen (simon) as early adopter testing changes
on cluster machines as well as all the testers and people
who provided feedback the last months on freebsd-jail and
other channels.
- My employer, CK Software GmbH, for the support so I could work on this.
Reviewed by: (see above)
MFC after: 3 months (this is just so that I get the mail)
X-MFC Before: 7.2-RELEASE if possible
2008-11-29 14:32:14 +00:00
|
|
|
}
|
|
|
|
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_sigaction(struct thread *td, struct freebsd32_sigaction_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
2003-04-22 18:23:49 +00:00
|
|
|
struct sigaction32 s32;
|
|
|
|
struct sigaction sa, osa, *sap;
|
2002-07-20 02:56:12 +00:00
|
|
|
int error;
|
|
|
|
|
2003-04-22 18:23:49 +00:00
|
|
|
if (uap->act) {
|
|
|
|
error = copyin(uap->act, &s32, sizeof(s32));
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
2003-04-22 18:23:49 +00:00
|
|
|
sa.sa_handler = PTRIN(s32.sa_u);
|
|
|
|
CP(s32, sa, sa_flags);
|
|
|
|
CP(s32, sa, sa_mask);
|
|
|
|
sap = &sa;
|
|
|
|
} else
|
|
|
|
sap = NULL;
|
|
|
|
error = kern_sigaction(td, uap->sig, sap, &osa, 0);
|
2005-05-24 17:52:14 +00:00
|
|
|
if (error == 0 && uap->oact != NULL) {
|
2003-04-22 18:23:49 +00:00
|
|
|
s32.sa_u = PTROUT(osa.sa_handler);
|
|
|
|
CP(osa, s32, sa_flags);
|
|
|
|
CP(osa, s32, sa_mask);
|
|
|
|
error = copyout(&s32, uap->oact, sizeof(s32));
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2003-05-14 04:10:49 +00:00
|
|
|
#ifdef COMPAT_FREEBSD4
|
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd4_freebsd32_sigaction(struct thread *td,
|
|
|
|
struct freebsd4_freebsd32_sigaction_args *uap)
|
2003-05-14 04:10:49 +00:00
|
|
|
{
|
|
|
|
struct sigaction32 s32;
|
|
|
|
struct sigaction sa, osa, *sap;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->act) {
|
|
|
|
error = copyin(uap->act, &s32, sizeof(s32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
sa.sa_handler = PTRIN(s32.sa_u);
|
|
|
|
CP(s32, sa, sa_flags);
|
|
|
|
CP(s32, sa, sa_mask);
|
|
|
|
sap = &sa;
|
|
|
|
} else
|
|
|
|
sap = NULL;
|
|
|
|
error = kern_sigaction(td, uap->sig, sap, &osa, KSA_FREEBSD4);
|
2005-05-24 17:52:14 +00:00
|
|
|
if (error == 0 && uap->oact != NULL) {
|
2003-05-14 04:10:49 +00:00
|
|
|
s32.sa_u = PTROUT(osa.sa_handler);
|
|
|
|
CP(osa, s32, sa_flags);
|
|
|
|
CP(osa, s32, sa_mask);
|
|
|
|
error = copyout(&s32, uap->oact, sizeof(s32));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2005-10-23 10:43:14 +00:00
|
|
|
#ifdef COMPAT_43
|
2005-10-26 22:19:51 +00:00
|
|
|
struct osigaction32 {
|
2005-10-23 10:43:14 +00:00
|
|
|
u_int32_t sa_u;
|
|
|
|
osigset_t sa_mask;
|
|
|
|
int sa_flags;
|
|
|
|
};
|
|
|
|
|
|
|
|
#define ONSIG 32
|
|
|
|
|
|
|
|
int
|
2005-10-26 22:19:51 +00:00
|
|
|
ofreebsd32_sigaction(struct thread *td,
|
|
|
|
struct ofreebsd32_sigaction_args *uap)
|
2005-10-23 10:43:14 +00:00
|
|
|
{
|
2005-10-26 22:19:51 +00:00
|
|
|
struct osigaction32 s32;
|
2005-10-23 10:43:14 +00:00
|
|
|
struct sigaction sa, osa, *sap;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->signum <= 0 || uap->signum >= ONSIG)
|
|
|
|
return (EINVAL);
|
|
|
|
|
|
|
|
if (uap->nsa) {
|
|
|
|
error = copyin(uap->nsa, &s32, sizeof(s32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
sa.sa_handler = PTRIN(s32.sa_u);
|
|
|
|
CP(s32, sa, sa_flags);
|
|
|
|
OSIG2SIG(s32.sa_mask, sa.sa_mask);
|
|
|
|
sap = &sa;
|
|
|
|
} else
|
|
|
|
sap = NULL;
|
|
|
|
error = kern_sigaction(td, uap->signum, sap, &osa, KSA_OSIGSET);
|
|
|
|
if (error == 0 && uap->osa != NULL) {
|
|
|
|
s32.sa_u = PTROUT(osa.sa_handler);
|
|
|
|
CP(osa, s32, sa_flags);
|
|
|
|
SIG2OSIG(osa.sa_mask, s32.sa_mask);
|
|
|
|
error = copyout(&s32, uap->osa, sizeof(s32));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
2005-10-26 22:19:51 +00:00
|
|
|
ofreebsd32_sigprocmask(struct thread *td,
|
|
|
|
struct ofreebsd32_sigprocmask_args *uap)
|
2005-10-23 10:43:14 +00:00
|
|
|
{
|
|
|
|
sigset_t set, oset;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
OSIG2SIG(uap->mask, set);
|
2009-10-27 10:47:58 +00:00
|
|
|
error = kern_sigprocmask(td, uap->how, &set, &oset, SIGPROCMASK_OLD);
|
2005-10-23 10:43:14 +00:00
|
|
|
SIG2OSIG(oset, td->td_retval[0]);
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
2005-10-26 22:19:51 +00:00
|
|
|
ofreebsd32_sigpending(struct thread *td,
|
|
|
|
struct ofreebsd32_sigpending_args *uap)
|
2005-10-23 10:43:14 +00:00
|
|
|
{
|
|
|
|
struct proc *p = td->td_proc;
|
|
|
|
sigset_t siglist;
|
|
|
|
|
|
|
|
PROC_LOCK(p);
|
|
|
|
siglist = p->p_siglist;
|
|
|
|
SIGSETOR(siglist, td->td_siglist);
|
|
|
|
PROC_UNLOCK(p);
|
|
|
|
SIG2OSIG(siglist, td->td_retval[0]);
|
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
struct sigvec32 {
|
|
|
|
u_int32_t sv_handler;
|
|
|
|
int sv_mask;
|
|
|
|
int sv_flags;
|
|
|
|
};
|
|
|
|
|
|
|
|
int
|
2005-10-26 22:19:51 +00:00
|
|
|
ofreebsd32_sigvec(struct thread *td,
|
|
|
|
struct ofreebsd32_sigvec_args *uap)
|
2005-10-23 10:43:14 +00:00
|
|
|
{
|
|
|
|
struct sigvec32 vec;
|
|
|
|
struct sigaction sa, osa, *sap;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->signum <= 0 || uap->signum >= ONSIG)
|
|
|
|
return (EINVAL);
|
|
|
|
|
|
|
|
if (uap->nsv) {
|
|
|
|
error = copyin(uap->nsv, &vec, sizeof(vec));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
sa.sa_handler = PTRIN(vec.sv_handler);
|
|
|
|
OSIG2SIG(vec.sv_mask, sa.sa_mask);
|
|
|
|
sa.sa_flags = vec.sv_flags;
|
|
|
|
sa.sa_flags ^= SA_RESTART;
|
|
|
|
sap = &sa;
|
|
|
|
} else
|
|
|
|
sap = NULL;
|
|
|
|
error = kern_sigaction(td, uap->signum, sap, &osa, KSA_OSIGSET);
|
|
|
|
if (error == 0 && uap->osv != NULL) {
|
|
|
|
vec.sv_handler = PTROUT(osa.sa_handler);
|
|
|
|
SIG2OSIG(osa.sa_mask, vec.sv_mask);
|
|
|
|
vec.sv_flags = osa.sa_flags;
|
|
|
|
vec.sv_flags &= ~SA_NOCLDWAIT;
|
|
|
|
vec.sv_flags ^= SA_RESTART;
|
|
|
|
error = copyout(&vec, uap->osv, sizeof(vec));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
2005-10-26 22:19:51 +00:00
|
|
|
ofreebsd32_sigblock(struct thread *td,
|
|
|
|
struct ofreebsd32_sigblock_args *uap)
|
2005-10-23 10:43:14 +00:00
|
|
|
{
|
2009-10-27 10:47:58 +00:00
|
|
|
sigset_t set, oset;
|
2005-10-23 10:43:14 +00:00
|
|
|
|
|
|
|
OSIG2SIG(uap->mask, set);
|
2009-10-27 10:47:58 +00:00
|
|
|
kern_sigprocmask(td, SIG_BLOCK, &set, &oset, 0);
|
|
|
|
SIG2OSIG(oset, td->td_retval[0]);
|
2005-10-23 10:43:14 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
2005-10-26 22:19:51 +00:00
|
|
|
ofreebsd32_sigsetmask(struct thread *td,
|
|
|
|
struct ofreebsd32_sigsetmask_args *uap)
|
2005-10-23 10:43:14 +00:00
|
|
|
{
|
2009-10-27 10:47:58 +00:00
|
|
|
sigset_t set, oset;
|
2005-10-23 10:43:14 +00:00
|
|
|
|
|
|
|
OSIG2SIG(uap->mask, set);
|
2009-10-27 10:47:58 +00:00
|
|
|
kern_sigprocmask(td, SIG_SETMASK, &set, &oset, 0);
|
|
|
|
SIG2OSIG(oset, td->td_retval[0]);
|
2005-10-23 10:43:14 +00:00
|
|
|
return (0);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
2005-10-26 22:19:51 +00:00
|
|
|
ofreebsd32_sigsuspend(struct thread *td,
|
|
|
|
struct ofreebsd32_sigsuspend_args *uap)
|
2005-10-23 10:43:14 +00:00
|
|
|
{
|
|
|
|
sigset_t mask;
|
|
|
|
|
|
|
|
OSIG2SIG(uap->mask, mask);
|
2009-10-27 10:42:24 +00:00
|
|
|
return (kern_sigsuspend(td, mask));
|
2005-10-23 10:43:14 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
struct sigstack32 {
|
|
|
|
u_int32_t ss_sp;
|
|
|
|
int ss_onstack;
|
|
|
|
};
|
|
|
|
|
|
|
|
int
|
2005-10-26 22:19:51 +00:00
|
|
|
ofreebsd32_sigstack(struct thread *td,
|
|
|
|
struct ofreebsd32_sigstack_args *uap)
|
2005-10-23 10:43:14 +00:00
|
|
|
{
|
|
|
|
struct sigstack32 s32;
|
|
|
|
struct sigstack nss, oss;
|
2007-06-17 04:37:57 +00:00
|
|
|
int error = 0, unss;
|
2005-10-23 10:43:14 +00:00
|
|
|
|
|
|
|
if (uap->nss != NULL) {
|
|
|
|
error = copyin(uap->nss, &s32, sizeof(s32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
nss.ss_sp = PTRIN(s32.ss_sp);
|
|
|
|
CP(s32, nss, ss_onstack);
|
2007-06-17 04:37:57 +00:00
|
|
|
unss = 1;
|
|
|
|
} else {
|
|
|
|
unss = 0;
|
2005-10-23 10:43:14 +00:00
|
|
|
}
|
|
|
|
oss.ss_sp = td->td_sigstk.ss_sp;
|
|
|
|
oss.ss_onstack = sigonstack(cpu_getstack(td));
|
2007-06-17 04:37:57 +00:00
|
|
|
if (unss) {
|
2005-10-23 10:43:14 +00:00
|
|
|
td->td_sigstk.ss_sp = nss.ss_sp;
|
|
|
|
td->td_sigstk.ss_size = 0;
|
2007-06-17 04:37:57 +00:00
|
|
|
td->td_sigstk.ss_flags |= (nss.ss_onstack & SS_ONSTACK);
|
2005-10-23 10:43:14 +00:00
|
|
|
td->td_pflags |= TDP_ALTSTACK;
|
|
|
|
}
|
|
|
|
if (uap->oss != NULL) {
|
|
|
|
s32.ss_sp = PTROUT(oss.ss_sp);
|
|
|
|
CP(oss, s32, ss_onstack);
|
|
|
|
error = copyout(&s32, uap->oss, sizeof(s32));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2005-01-19 17:44:59 +00:00
|
|
|
int
|
|
|
|
freebsd32_nanosleep(struct thread *td, struct freebsd32_nanosleep_args *uap)
|
2017-03-19 00:51:12 +00:00
|
|
|
{
|
|
|
|
|
|
|
|
return (freebsd32_user_clock_nanosleep(td, CLOCK_REALTIME,
|
|
|
|
TIMER_RELTIME, uap->rqtp, uap->rmtp));
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_clock_nanosleep(struct thread *td,
|
|
|
|
struct freebsd32_clock_nanosleep_args *uap)
|
|
|
|
{
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = freebsd32_user_clock_nanosleep(td, uap->clock_id, uap->flags,
|
|
|
|
uap->rqtp, uap->rmtp);
|
|
|
|
return (kern_posix_error(td, error));
|
|
|
|
}
|
|
|
|
|
|
|
|
static int
|
|
|
|
freebsd32_user_clock_nanosleep(struct thread *td, clockid_t clock_id,
|
|
|
|
int flags, const struct timespec32 *ua_rqtp, struct timespec32 *ua_rmtp)
|
2005-01-19 17:44:59 +00:00
|
|
|
{
|
|
|
|
struct timespec32 rmt32, rqt32;
|
|
|
|
struct timespec rmt, rqt;
|
|
|
|
int error;
|
|
|
|
|
2017-03-19 00:51:12 +00:00
|
|
|
error = copyin(ua_rqtp, &rqt32, sizeof(rqt32));
|
2005-01-19 17:44:59 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
|
|
|
|
CP(rqt32, rqt, tv_sec);
|
|
|
|
CP(rqt32, rqt, tv_nsec);
|
|
|
|
|
2017-03-19 00:51:12 +00:00
|
|
|
if (ua_rmtp != NULL && (flags & TIMER_ABSTIME) == 0 &&
|
|
|
|
!useracc(ua_rmtp, sizeof(rmt32), VM_PROT_WRITE))
|
2005-01-19 17:44:59 +00:00
|
|
|
return (EFAULT);
|
2017-03-19 00:51:12 +00:00
|
|
|
error = kern_clock_nanosleep(td, clock_id, flags, &rqt, &rmt);
|
|
|
|
if (error == EINTR && ua_rmtp != NULL && (flags & TIMER_ABSTIME) == 0) {
|
2005-01-19 17:44:59 +00:00
|
|
|
int error2;
|
|
|
|
|
|
|
|
CP(rmt, rmt32, tv_sec);
|
|
|
|
CP(rmt, rmt32, tv_nsec);
|
|
|
|
|
2017-03-19 00:51:12 +00:00
|
|
|
error2 = copyout(&rmt32, ua_rmtp, sizeof(rmt32));
|
2005-01-19 17:44:59 +00:00
|
|
|
if (error2)
|
|
|
|
error = error2;
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2005-10-15 02:54:18 +00:00
|
|
|
int
|
|
|
|
freebsd32_clock_gettime(struct thread *td,
|
|
|
|
struct freebsd32_clock_gettime_args *uap)
|
|
|
|
{
|
|
|
|
struct timespec ats;
|
|
|
|
struct timespec32 ats32;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = kern_clock_gettime(td, uap->clock_id, &ats);
|
|
|
|
if (error == 0) {
|
|
|
|
CP(ats, ats32, tv_sec);
|
|
|
|
CP(ats, ats32, tv_nsec);
|
|
|
|
error = copyout(&ats32, uap->tp, sizeof(ats32));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_clock_settime(struct thread *td,
|
|
|
|
struct freebsd32_clock_settime_args *uap)
|
|
|
|
{
|
|
|
|
struct timespec ats;
|
|
|
|
struct timespec32 ats32;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = copyin(uap->tp, &ats32, sizeof(ats32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
CP(ats32, ats, tv_sec);
|
|
|
|
CP(ats32, ats, tv_nsec);
|
|
|
|
|
|
|
|
return (kern_clock_settime(td, uap->clock_id, &ats));
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_clock_getres(struct thread *td,
|
|
|
|
struct freebsd32_clock_getres_args *uap)
|
|
|
|
{
|
|
|
|
struct timespec ts;
|
|
|
|
struct timespec32 ts32;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->tp == NULL)
|
|
|
|
return (0);
|
|
|
|
error = kern_clock_getres(td, uap->clock_id, &ts);
|
|
|
|
if (error == 0) {
|
|
|
|
CP(ts, ts32, tv_sec);
|
|
|
|
CP(ts, ts32, tv_nsec);
|
|
|
|
error = copyout(&ts32, uap->tp, sizeof(ts32));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2013-07-21 19:43:52 +00:00
|
|
|
int freebsd32_ktimer_create(struct thread *td,
|
|
|
|
struct freebsd32_ktimer_create_args *uap)
|
|
|
|
{
|
|
|
|
struct sigevent32 ev32;
|
|
|
|
struct sigevent ev, *evp;
|
|
|
|
int error, id;
|
|
|
|
|
|
|
|
if (uap->evp == NULL) {
|
|
|
|
evp = NULL;
|
|
|
|
} else {
|
|
|
|
evp = &ev;
|
|
|
|
error = copyin(uap->evp, &ev32, sizeof(ev32));
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
error = convert_sigevent32(&ev32, &ev);
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
error = kern_ktimer_create(td, uap->clock_id, evp, &id, -1);
|
|
|
|
if (error == 0) {
|
|
|
|
error = copyout(&id, uap->timerid, sizeof(int));
|
|
|
|
if (error != 0)
|
|
|
|
kern_ktimer_delete(td, id);
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_ktimer_settime(struct thread *td,
|
|
|
|
struct freebsd32_ktimer_settime_args *uap)
|
|
|
|
{
|
|
|
|
struct itimerspec32 val32, oval32;
|
|
|
|
struct itimerspec val, oval, *ovalp;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = copyin(uap->value, &val32, sizeof(val32));
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
ITS_CP(val32, val);
|
|
|
|
ovalp = uap->ovalue != NULL ? &oval : NULL;
|
|
|
|
error = kern_ktimer_settime(td, uap->timerid, uap->flags, &val, ovalp);
|
|
|
|
if (error == 0 && uap->ovalue != NULL) {
|
|
|
|
ITS_CP(oval, oval32);
|
|
|
|
error = copyout(&oval32, uap->ovalue, sizeof(oval32));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_ktimer_gettime(struct thread *td,
|
|
|
|
struct freebsd32_ktimer_gettime_args *uap)
|
|
|
|
{
|
|
|
|
struct itimerspec32 val32;
|
|
|
|
struct itimerspec val;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = kern_ktimer_gettime(td, uap->timerid, &val);
|
|
|
|
if (error == 0) {
|
|
|
|
ITS_CP(val, val32);
|
|
|
|
error = copyout(&val32, uap->value, sizeof(val32));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2013-07-20 13:39:41 +00:00
|
|
|
int
|
|
|
|
freebsd32_clock_getcpuclockid2(struct thread *td,
|
|
|
|
struct freebsd32_clock_getcpuclockid2_args *uap)
|
|
|
|
{
|
|
|
|
clockid_t clk_id;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = kern_clock_getcpuclockid2(td, PAIR32TO64(id_t, uap->id),
|
|
|
|
uap->which, &clk_id);
|
|
|
|
if (error == 0)
|
|
|
|
error = copyout(&clk_id, uap->clock_id, sizeof(clockid_t));
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2006-09-22 15:04:28 +00:00
|
|
|
int
|
|
|
|
freebsd32_thr_new(struct thread *td,
|
|
|
|
struct freebsd32_thr_new_args *uap)
|
|
|
|
{
|
|
|
|
struct thr_param32 param32;
|
|
|
|
struct thr_param param;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->param_size < 0 ||
|
|
|
|
uap->param_size > sizeof(struct thr_param32))
|
|
|
|
return (EINVAL);
|
|
|
|
bzero(¶m, sizeof(struct thr_param));
|
|
|
|
bzero(¶m32, sizeof(struct thr_param32));
|
|
|
|
error = copyin(uap->param, ¶m32, uap->param_size);
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
param.start_func = PTRIN(param32.start_func);
|
|
|
|
param.arg = PTRIN(param32.arg);
|
|
|
|
param.stack_base = PTRIN(param32.stack_base);
|
|
|
|
param.stack_size = param32.stack_size;
|
|
|
|
param.tls_base = PTRIN(param32.tls_base);
|
|
|
|
param.tls_size = param32.tls_size;
|
|
|
|
param.child_tid = PTRIN(param32.child_tid);
|
|
|
|
param.parent_tid = PTRIN(param32.parent_tid);
|
|
|
|
param.flags = param32.flags;
|
|
|
|
param.rtp = PTRIN(param32.rtp);
|
|
|
|
param.spare[0] = PTRIN(param32.spare[0]);
|
|
|
|
param.spare[1] = PTRIN(param32.spare[1]);
|
|
|
|
param.spare[2] = PTRIN(param32.spare[2]);
|
|
|
|
|
|
|
|
return (kern_thr_new(td, ¶m));
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_thr_suspend(struct thread *td, struct freebsd32_thr_suspend_args *uap)
|
|
|
|
{
|
|
|
|
struct timespec32 ts32;
|
|
|
|
struct timespec ts, *tsp;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = 0;
|
|
|
|
tsp = NULL;
|
|
|
|
if (uap->timeout != NULL) {
|
|
|
|
error = copyin((const void *)uap->timeout, (void *)&ts32,
|
|
|
|
sizeof(struct timespec32));
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
ts.tv_sec = ts32.tv_sec;
|
|
|
|
ts.tv_nsec = ts32.tv_nsec;
|
|
|
|
tsp = &ts;
|
|
|
|
}
|
|
|
|
return (kern_thr_suspend(td, tsp));
|
|
|
|
}
|
|
|
|
|
2006-10-05 01:56:11 +00:00
|
|
|
void
|
2010-07-04 11:43:53 +00:00
|
|
|
siginfo_to_siginfo32(const siginfo_t *src, struct siginfo32 *dst)
|
2006-10-05 01:56:11 +00:00
|
|
|
{
|
|
|
|
bzero(dst, sizeof(*dst));
|
|
|
|
dst->si_signo = src->si_signo;
|
|
|
|
dst->si_errno = src->si_errno;
|
|
|
|
dst->si_code = src->si_code;
|
|
|
|
dst->si_pid = src->si_pid;
|
|
|
|
dst->si_uid = src->si_uid;
|
|
|
|
dst->si_status = src->si_status;
|
2008-11-10 23:36:20 +00:00
|
|
|
dst->si_addr = (uintptr_t)src->si_addr;
|
2013-07-21 19:17:46 +00:00
|
|
|
dst->si_value.sival_int = src->si_value.sival_int;
|
2006-10-05 01:56:11 +00:00
|
|
|
dst->si_timerid = src->si_timerid;
|
|
|
|
dst->si_overrun = src->si_overrun;
|
|
|
|
}
|
|
|
|
|
2017-05-05 18:49:39 +00:00
|
|
|
#ifndef _FREEBSD32_SYSPROTO_H_
|
|
|
|
struct freebsd32_sigqueue_args {
|
|
|
|
pid_t pid;
|
|
|
|
int signum;
|
|
|
|
/* union sigval32 */ int value;
|
|
|
|
};
|
|
|
|
#endif
|
|
|
|
int
|
|
|
|
freebsd32_sigqueue(struct thread *td, struct freebsd32_sigqueue_args *uap)
|
|
|
|
{
|
|
|
|
union sigval sv;
|
|
|
|
|
|
|
|
/*
|
|
|
|
* On 32-bit ABIs, sival_int and sival_ptr are the same.
|
|
|
|
* On 64-bit little-endian ABIs, the low bits are the same.
|
|
|
|
* In 64-bit big-endian ABIs, sival_int overlaps with
|
|
|
|
* sival_ptr's HIGH bits. We choose to support sival_int
|
|
|
|
* rather than sival_ptr in this case as it seems to be
|
|
|
|
* more common.
|
|
|
|
*/
|
|
|
|
bzero(&sv, sizeof(sv));
|
|
|
|
sv.sival_int = uap->value;
|
|
|
|
|
|
|
|
return (kern_sigqueue(td, uap->pid, uap->signum, &sv));
|
|
|
|
}
|
|
|
|
|
2006-10-05 01:56:11 +00:00
|
|
|
int
|
|
|
|
freebsd32_sigtimedwait(struct thread *td, struct freebsd32_sigtimedwait_args *uap)
|
|
|
|
{
|
|
|
|
struct timespec32 ts32;
|
|
|
|
struct timespec ts;
|
|
|
|
struct timespec *timeout;
|
|
|
|
sigset_t set;
|
|
|
|
ksiginfo_t ksi;
|
|
|
|
struct siginfo32 si32;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->timeout) {
|
|
|
|
error = copyin(uap->timeout, &ts32, sizeof(ts32));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
ts.tv_sec = ts32.tv_sec;
|
|
|
|
ts.tv_nsec = ts32.tv_nsec;
|
|
|
|
timeout = &ts;
|
|
|
|
} else
|
|
|
|
timeout = NULL;
|
|
|
|
|
|
|
|
error = copyin(uap->set, &set, sizeof(set));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
|
|
|
|
error = kern_sigtimedwait(td, set, &ksi, timeout);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
|
|
|
|
if (uap->info) {
|
|
|
|
siginfo_to_siginfo32(&ksi.ksi_info, &si32);
|
|
|
|
error = copyout(&si32, uap->info, sizeof(struct siginfo32));
|
|
|
|
}
|
|
|
|
|
|
|
|
if (error == 0)
|
|
|
|
td->td_retval[0] = ksi.ksi_signo;
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* MPSAFE
|
|
|
|
*/
|
|
|
|
int
|
|
|
|
freebsd32_sigwaitinfo(struct thread *td, struct freebsd32_sigwaitinfo_args *uap)
|
|
|
|
{
|
|
|
|
ksiginfo_t ksi;
|
|
|
|
struct siginfo32 si32;
|
|
|
|
sigset_t set;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = copyin(uap->set, &set, sizeof(set));
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
|
|
|
|
error = kern_sigtimedwait(td, set, &ksi, NULL);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
|
|
|
|
if (uap->info) {
|
|
|
|
siginfo_to_siginfo32(&ksi.ksi_info, &si32);
|
|
|
|
error = copyout(&si32, uap->info, sizeof(struct siginfo32));
|
|
|
|
}
|
|
|
|
if (error == 0)
|
|
|
|
td->td_retval[0] = ksi.ksi_signo;
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
|
2008-07-10 17:45:57 +00:00
|
|
|
int
|
|
|
|
freebsd32_cpuset_setid(struct thread *td,
|
|
|
|
struct freebsd32_cpuset_setid_args *uap)
|
|
|
|
{
|
|
|
|
|
2017-01-31 15:11:23 +00:00
|
|
|
return (kern_cpuset_setid(td, uap->which,
|
|
|
|
PAIR32TO64(id_t, uap->id), uap->setid));
|
2008-07-10 17:45:57 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_cpuset_getid(struct thread *td,
|
|
|
|
struct freebsd32_cpuset_getid_args *uap)
|
|
|
|
{
|
|
|
|
|
2017-01-31 15:11:23 +00:00
|
|
|
return (kern_cpuset_getid(td, uap->level, uap->which,
|
|
|
|
PAIR32TO64(id_t, uap->id), uap->setid));
|
2008-07-10 17:45:57 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_cpuset_getaffinity(struct thread *td,
|
|
|
|
struct freebsd32_cpuset_getaffinity_args *uap)
|
|
|
|
{
|
|
|
|
|
2017-02-05 13:24:54 +00:00
|
|
|
return (kern_cpuset_getaffinity(td, uap->level, uap->which,
|
|
|
|
PAIR32TO64(id_t,uap->id), uap->cpusetsize, uap->mask));
|
2008-07-10 17:45:57 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_cpuset_setaffinity(struct thread *td,
|
|
|
|
struct freebsd32_cpuset_setaffinity_args *uap)
|
|
|
|
{
|
|
|
|
|
2017-02-05 13:24:54 +00:00
|
|
|
return (kern_cpuset_setaffinity(td, uap->level, uap->which,
|
|
|
|
PAIR32TO64(id_t,uap->id), uap->cpusetsize, uap->mask));
|
2008-07-10 17:45:57 +00:00
|
|
|
}
|
|
|
|
|
2018-01-12 22:48:23 +00:00
|
|
|
int
|
|
|
|
freebsd32_cpuset_getdomain(struct thread *td,
|
|
|
|
struct freebsd32_cpuset_getdomain_args *uap)
|
|
|
|
{
|
|
|
|
|
|
|
|
return (kern_cpuset_getdomain(td, uap->level, uap->which,
|
|
|
|
PAIR32TO64(id_t,uap->id), uap->domainsetsize, uap->mask, uap->policy));
|
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_cpuset_setdomain(struct thread *td,
|
|
|
|
struct freebsd32_cpuset_setdomain_args *uap)
|
|
|
|
{
|
|
|
|
|
|
|
|
return (kern_cpuset_setdomain(td, uap->level, uap->which,
|
|
|
|
PAIR32TO64(id_t,uap->id), uap->domainsetsize, uap->mask, uap->policy));
|
|
|
|
}
|
|
|
|
|
2008-09-19 15:17:32 +00:00
|
|
|
int
|
|
|
|
freebsd32_nmount(struct thread *td,
|
|
|
|
struct freebsd32_nmount_args /* {
|
|
|
|
struct iovec *iovp;
|
|
|
|
unsigned int iovcnt;
|
|
|
|
int flags;
|
|
|
|
} */ *uap)
|
|
|
|
{
|
|
|
|
struct uio *auio;
|
2012-01-17 01:08:01 +00:00
|
|
|
uint64_t flags;
|
2009-03-02 23:26:30 +00:00
|
|
|
int error;
|
2008-09-19 15:17:32 +00:00
|
|
|
|
2012-01-17 01:08:01 +00:00
|
|
|
/*
|
|
|
|
* Mount flags are now 64-bits. On 32-bit archtectures only
|
|
|
|
* 32-bits are passed in, but from here on everything handles
|
|
|
|
* 64-bit flags correctly.
|
|
|
|
*/
|
|
|
|
flags = uap->flags;
|
|
|
|
|
|
|
|
AUDIT_ARG_FFLAGS(flags);
|
2008-09-19 15:17:32 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* Filter out MNT_ROOTFS. We do not want clients of nmount() in
|
|
|
|
* userspace to set this flag, but we must filter it out if we want
|
|
|
|
* MNT_UPDATE on the root file system to work.
|
2010-11-23 13:49:15 +00:00
|
|
|
* MNT_ROOTFS should only be set by the kernel when mounting its
|
|
|
|
* root file system.
|
2008-09-19 15:17:32 +00:00
|
|
|
*/
|
2012-01-17 01:08:01 +00:00
|
|
|
flags &= ~MNT_ROOTFS;
|
2008-09-19 15:17:32 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* check that we have an even number of iovec's
|
|
|
|
* and that we have at least two options.
|
|
|
|
*/
|
|
|
|
if ((uap->iovcnt & 1) || (uap->iovcnt < 4))
|
|
|
|
return (EINVAL);
|
2002-07-20 02:56:12 +00:00
|
|
|
|
2008-09-19 15:17:32 +00:00
|
|
|
error = freebsd32_copyinuio(uap->iovp, uap->iovcnt, &auio);
|
|
|
|
if (error)
|
|
|
|
return (error);
|
2012-01-17 01:08:01 +00:00
|
|
|
error = vfs_donmount(td, flags, auio);
|
2009-03-02 23:26:30 +00:00
|
|
|
|
2008-09-19 15:17:32 +00:00
|
|
|
free(auio, M_IOV);
|
|
|
|
return error;
|
|
|
|
}
|
|
|
|
|
|
|
|
#if 0
|
2002-07-20 02:56:12 +00:00
|
|
|
int
|
2003-08-22 23:07:28 +00:00
|
|
|
freebsd32_xxx(struct thread *td, struct freebsd32_xxx_args *uap)
|
2002-07-20 02:56:12 +00:00
|
|
|
{
|
|
|
|
struct yyy32 *p32, s32;
|
|
|
|
struct yyy *p = NULL, s;
|
2008-09-15 17:39:40 +00:00
|
|
|
struct xxx_arg ap;
|
|
|
|
int error;
|
2002-07-20 02:56:12 +00:00
|
|
|
|
2005-06-29 15:16:20 +00:00
|
|
|
if (uap->zzz) {
|
|
|
|
error = copyin(uap->zzz, &s32, sizeof(s32));
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
|
|
|
/* translate in */
|
2005-06-29 15:16:20 +00:00
|
|
|
p = &s;
|
2002-07-20 02:56:12 +00:00
|
|
|
}
|
2005-06-29 15:16:20 +00:00
|
|
|
error = kern_xxx(td, p);
|
2002-07-20 02:56:12 +00:00
|
|
|
if (error)
|
|
|
|
return (error);
|
2005-06-29 15:16:20 +00:00
|
|
|
if (uap->zzz) {
|
2002-07-20 02:56:12 +00:00
|
|
|
/* translate out */
|
|
|
|
error = copyout(&s32, p32, sizeof(s32));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|
|
|
|
#endif
|
2008-09-25 20:50:21 +00:00
|
|
|
|
|
|
|
int
|
|
|
|
syscall32_module_handler(struct module *mod, int what, void *arg)
|
|
|
|
{
|
|
|
|
|
2018-02-20 18:08:57 +00:00
|
|
|
return (kern_syscall_module_handler(freebsd32_sysent, mod, what, arg));
|
2008-09-25 20:50:21 +00:00
|
|
|
}
|
2010-03-11 14:49:06 +00:00
|
|
|
|
2010-03-19 10:56:30 +00:00
|
|
|
int
|
2014-10-26 19:42:44 +00:00
|
|
|
syscall32_helper_register(struct syscall_helper_data *sd, int flags)
|
2010-03-19 10:56:30 +00:00
|
|
|
{
|
|
|
|
|
2018-02-20 18:08:57 +00:00
|
|
|
return (kern_syscall_helper_register(freebsd32_sysent, sd, flags));
|
2010-03-19 10:56:30 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
syscall32_helper_unregister(struct syscall_helper_data *sd)
|
|
|
|
{
|
|
|
|
|
2018-02-20 18:08:57 +00:00
|
|
|
return (kern_syscall_helper_unregister(freebsd32_sysent, sd));
|
2010-03-19 10:56:30 +00:00
|
|
|
}
|
|
|
|
|
2010-03-11 14:49:06 +00:00
|
|
|
register_t *
|
|
|
|
freebsd32_copyout_strings(struct image_params *imgp)
|
|
|
|
{
|
2010-08-17 08:55:45 +00:00
|
|
|
int argc, envc, i;
|
2010-03-11 14:49:06 +00:00
|
|
|
u_int32_t *vectp;
|
2014-03-19 12:35:04 +00:00
|
|
|
char *stringp;
|
|
|
|
uintptr_t destp;
|
2010-03-11 14:49:06 +00:00
|
|
|
u_int32_t *stack_base;
|
|
|
|
struct freebsd32_ps_strings *arginfo;
|
2010-08-17 08:55:45 +00:00
|
|
|
char canary[sizeof(long) * 8];
|
|
|
|
int32_t pagesizes32[MAXPAGESIZES];
|
2010-03-11 14:49:06 +00:00
|
|
|
size_t execpath_len;
|
|
|
|
int szsigcode;
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Calculate string base and vector table pointers.
|
|
|
|
* Also deal with signal trampoline code for this exec type.
|
|
|
|
*/
|
|
|
|
if (imgp->execpath != NULL && imgp->auxargs != NULL)
|
|
|
|
execpath_len = strlen(imgp->execpath) + 1;
|
|
|
|
else
|
|
|
|
execpath_len = 0;
|
2010-08-07 11:57:13 +00:00
|
|
|
arginfo = (struct freebsd32_ps_strings *)curproc->p_sysent->
|
|
|
|
sv_psstrings;
|
2011-01-08 16:13:44 +00:00
|
|
|
if (imgp->proc->p_sysent->sv_sigcode_base == 0)
|
|
|
|
szsigcode = *(imgp->proc->p_sysent->sv_szsigcode);
|
|
|
|
else
|
|
|
|
szsigcode = 0;
|
2014-03-19 12:35:04 +00:00
|
|
|
destp = (uintptr_t)arginfo;
|
2010-03-11 14:49:06 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* install sigcode
|
|
|
|
*/
|
2014-03-19 12:35:04 +00:00
|
|
|
if (szsigcode != 0) {
|
|
|
|
destp -= szsigcode;
|
|
|
|
destp = rounddown2(destp, sizeof(uint32_t));
|
|
|
|
copyout(imgp->proc->p_sysent->sv_sigcode, (void *)destp,
|
|
|
|
szsigcode);
|
|
|
|
}
|
2010-03-11 14:49:06 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* Copy the image path for the rtld.
|
|
|
|
*/
|
|
|
|
if (execpath_len != 0) {
|
2014-03-19 12:35:04 +00:00
|
|
|
destp -= execpath_len;
|
|
|
|
imgp->execpathp = destp;
|
|
|
|
copyout(imgp->execpath, (void *)destp, execpath_len);
|
2010-03-11 14:49:06 +00:00
|
|
|
}
|
|
|
|
|
2010-08-17 08:55:45 +00:00
|
|
|
/*
|
|
|
|
* Prepare the canary for SSP.
|
|
|
|
*/
|
|
|
|
arc4rand(canary, sizeof(canary), 0);
|
2014-03-19 12:35:04 +00:00
|
|
|
destp -= sizeof(canary);
|
|
|
|
imgp->canary = destp;
|
|
|
|
copyout(canary, (void *)destp, sizeof(canary));
|
2010-08-17 08:55:45 +00:00
|
|
|
imgp->canarylen = sizeof(canary);
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Prepare the pagesizes array.
|
|
|
|
*/
|
|
|
|
for (i = 0; i < MAXPAGESIZES; i++)
|
|
|
|
pagesizes32[i] = (uint32_t)pagesizes[i];
|
2014-03-19 12:35:04 +00:00
|
|
|
destp -= sizeof(pagesizes32);
|
|
|
|
destp = rounddown2(destp, sizeof(uint32_t));
|
|
|
|
imgp->pagesizes = destp;
|
|
|
|
copyout(pagesizes32, (void *)destp, sizeof(pagesizes32));
|
2010-08-17 08:55:45 +00:00
|
|
|
imgp->pagesizeslen = sizeof(pagesizes32);
|
|
|
|
|
2014-03-19 12:35:04 +00:00
|
|
|
destp -= ARG_MAX - imgp->args->stringspace;
|
|
|
|
destp = rounddown2(destp, sizeof(uint32_t));
|
|
|
|
|
2018-04-19 16:00:34 +00:00
|
|
|
vectp = (uint32_t *)destp;
|
2019-07-31 20:23:10 +00:00
|
|
|
if (imgp->sysent->sv_stackgap != NULL)
|
|
|
|
imgp->sysent->sv_stackgap(imgp, (u_long *)&vectp);
|
|
|
|
|
2010-03-11 14:49:06 +00:00
|
|
|
if (imgp->auxargs) {
|
|
|
|
/*
|
2018-04-19 16:00:34 +00:00
|
|
|
* Allocate room on the stack for the ELF auxargs
|
|
|
|
* array. It has up to AT_COUNT entries.
|
2010-03-11 14:49:06 +00:00
|
|
|
*/
|
2018-04-19 16:00:34 +00:00
|
|
|
vectp -= howmany(AT_COUNT * sizeof(Elf32_Auxinfo),
|
|
|
|
sizeof(*vectp));
|
2014-03-19 12:35:04 +00:00
|
|
|
}
|
2010-03-11 14:49:06 +00:00
|
|
|
|
2018-04-19 16:00:34 +00:00
|
|
|
/*
|
|
|
|
* Allocate room for the argv[] and env vectors including the
|
|
|
|
* terminating NULL pointers.
|
|
|
|
*/
|
|
|
|
vectp -= imgp->args->argc + 1 + imgp->args->envc + 1;
|
|
|
|
|
2010-03-11 14:49:06 +00:00
|
|
|
/*
|
|
|
|
* vectp also becomes our initial stack base
|
|
|
|
*/
|
|
|
|
stack_base = vectp;
|
|
|
|
|
|
|
|
stringp = imgp->args->begin_argv;
|
|
|
|
argc = imgp->args->argc;
|
|
|
|
envc = imgp->args->envc;
|
|
|
|
/*
|
|
|
|
* Copy out strings - arguments and environment.
|
|
|
|
*/
|
2014-03-19 12:35:04 +00:00
|
|
|
copyout(stringp, (void *)destp, ARG_MAX - imgp->args->stringspace);
|
2010-03-11 14:49:06 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* Fill in "ps_strings" struct for ps, w, etc.
|
|
|
|
*/
|
|
|
|
suword32(&arginfo->ps_argvstr, (u_int32_t)(intptr_t)vectp);
|
|
|
|
suword32(&arginfo->ps_nargvstr, argc);
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Fill in argument portion of vector table.
|
|
|
|
*/
|
|
|
|
for (; argc > 0; --argc) {
|
|
|
|
suword32(vectp++, (u_int32_t)(intptr_t)destp);
|
|
|
|
while (*stringp++ != 0)
|
|
|
|
destp++;
|
|
|
|
destp++;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* a null vector table pointer separates the argp's from the envp's */
|
|
|
|
suword32(vectp++, 0);
|
|
|
|
|
|
|
|
suword32(&arginfo->ps_envstr, (u_int32_t)(intptr_t)vectp);
|
|
|
|
suword32(&arginfo->ps_nenvstr, envc);
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Fill in environment portion of vector table.
|
|
|
|
*/
|
|
|
|
for (; envc > 0; --envc) {
|
|
|
|
suword32(vectp++, (u_int32_t)(intptr_t)destp);
|
|
|
|
while (*stringp++ != 0)
|
|
|
|
destp++;
|
|
|
|
destp++;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* end of vector table is a null pointer */
|
|
|
|
suword32(vectp, 0);
|
|
|
|
|
|
|
|
return ((register_t *)stack_base);
|
|
|
|
}
|
|
|
|
|
2011-03-30 14:46:12 +00:00
|
|
|
int
|
|
|
|
freebsd32_kldstat(struct thread *td, struct freebsd32_kldstat_args *uap)
|
|
|
|
{
|
2017-11-15 22:30:21 +00:00
|
|
|
struct kld_file_stat *stat;
|
|
|
|
struct kld32_file_stat *stat32;
|
2011-03-30 14:46:12 +00:00
|
|
|
int error, version;
|
|
|
|
|
|
|
|
if ((error = copyin(&uap->stat->version, &version, sizeof(version)))
|
|
|
|
!= 0)
|
|
|
|
return (error);
|
|
|
|
if (version != sizeof(struct kld32_file_stat_1) &&
|
|
|
|
version != sizeof(struct kld32_file_stat))
|
|
|
|
return (EINVAL);
|
|
|
|
|
2017-11-15 22:30:21 +00:00
|
|
|
stat = malloc(sizeof(*stat), M_TEMP, M_WAITOK | M_ZERO);
|
|
|
|
stat32 = malloc(sizeof(*stat32), M_TEMP, M_WAITOK | M_ZERO);
|
|
|
|
error = kern_kldstat(td, uap->fileid, stat);
|
|
|
|
if (error == 0) {
|
|
|
|
bcopy(&stat->name[0], &stat32->name[0], sizeof(stat->name));
|
|
|
|
CP(*stat, *stat32, refs);
|
|
|
|
CP(*stat, *stat32, id);
|
|
|
|
PTROUT_CP(*stat, *stat32, address);
|
|
|
|
CP(*stat, *stat32, size);
|
|
|
|
bcopy(&stat->pathname[0], &stat32->pathname[0],
|
|
|
|
sizeof(stat->pathname));
|
2018-03-27 18:05:51 +00:00
|
|
|
stat32->version = version;
|
2017-11-15 22:30:21 +00:00
|
|
|
error = copyout(stat32, uap->stat, version);
|
|
|
|
}
|
|
|
|
free(stat, M_TEMP);
|
|
|
|
free(stat32, M_TEMP);
|
|
|
|
return (error);
|
2011-03-30 14:46:12 +00:00
|
|
|
}
|
2011-04-18 16:32:22 +00:00
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_posix_fallocate(struct thread *td,
|
|
|
|
struct freebsd32_posix_fallocate_args *uap)
|
|
|
|
{
|
2016-02-25 19:58:23 +00:00
|
|
|
int error;
|
2011-04-18 16:32:22 +00:00
|
|
|
|
2016-02-25 19:58:23 +00:00
|
|
|
error = kern_posix_fallocate(td, uap->fd,
|
2014-01-23 17:24:26 +00:00
|
|
|
PAIR32TO64(off_t, uap->offset), PAIR32TO64(off_t, uap->len));
|
2016-02-25 19:58:23 +00:00
|
|
|
return (kern_posix_error(td, error));
|
2011-04-18 16:32:22 +00:00
|
|
|
}
|
2011-11-04 04:02:50 +00:00
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_posix_fadvise(struct thread *td,
|
|
|
|
struct freebsd32_posix_fadvise_args *uap)
|
|
|
|
{
|
2016-02-25 19:58:23 +00:00
|
|
|
int error;
|
2011-11-04 04:02:50 +00:00
|
|
|
|
2016-02-25 19:58:23 +00:00
|
|
|
error = kern_posix_fadvise(td, uap->fd, PAIR32TO64(off_t, uap->offset),
|
|
|
|
PAIR32TO64(off_t, uap->len), uap->advice);
|
|
|
|
return (kern_posix_error(td, error));
|
2011-11-04 04:02:50 +00:00
|
|
|
}
|
2013-07-21 19:33:48 +00:00
|
|
|
|
|
|
|
int
|
|
|
|
convert_sigevent32(struct sigevent32 *sig32, struct sigevent *sig)
|
|
|
|
{
|
|
|
|
|
|
|
|
CP(*sig32, *sig, sigev_notify);
|
|
|
|
switch (sig->sigev_notify) {
|
|
|
|
case SIGEV_NONE:
|
|
|
|
break;
|
|
|
|
case SIGEV_THREAD_ID:
|
|
|
|
CP(*sig32, *sig, sigev_notify_thread_id);
|
|
|
|
/* FALLTHROUGH */
|
|
|
|
case SIGEV_SIGNAL:
|
|
|
|
CP(*sig32, *sig, sigev_signo);
|
|
|
|
PTRIN_CP(*sig32, *sig, sigev_value.sival_ptr);
|
|
|
|
break;
|
|
|
|
case SIGEV_KEVENT:
|
|
|
|
CP(*sig32, *sig, sigev_notify_kqueue);
|
|
|
|
CP(*sig32, *sig, sigev_notify_kevent_flags);
|
|
|
|
PTRIN_CP(*sig32, *sig, sigev_value.sival_ptr);
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
return (EINVAL);
|
|
|
|
}
|
|
|
|
return (0);
|
|
|
|
}
|
2013-09-19 18:53:42 +00:00
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_procctl(struct thread *td, struct freebsd32_procctl_args *uap)
|
|
|
|
{
|
|
|
|
void *data;
|
2014-12-15 12:01:42 +00:00
|
|
|
union {
|
|
|
|
struct procctl_reaper_status rs;
|
|
|
|
struct procctl_reaper_pids rp;
|
|
|
|
struct procctl_reaper_kill rk;
|
|
|
|
} x;
|
|
|
|
union {
|
|
|
|
struct procctl_reaper_pids32 rp;
|
|
|
|
} x32;
|
2018-04-18 21:31:13 +00:00
|
|
|
int error, error1, flags, signum;
|
2013-09-19 18:53:42 +00:00
|
|
|
|
2019-03-16 11:44:33 +00:00
|
|
|
if (uap->com >= PROC_PROCCTL_MD_MIN)
|
|
|
|
return (cpu_procctl(td, uap->idtype, PAIR32TO64(id_t, uap->id),
|
|
|
|
uap->com, PTRIN(uap->data)));
|
|
|
|
|
2013-09-19 18:53:42 +00:00
|
|
|
switch (uap->com) {
|
Implement Address Space Layout Randomization (ASLR)
With this change, randomization can be enabled for all non-fixed
mappings. It means that the base address for the mapping is selected
with a guaranteed amount of entropy (bits). If the mapping was
requested to be superpage aligned, the randomization honours the
superpage attributes.
Although the value of ASLR is diminshing over time as exploit authors
work out simple ASLR bypass techniques, it elimintates the trivial
exploitation of certain vulnerabilities, at least in theory. This
implementation is relatively small and happens at the correct
architectural level. Also, it is not expected to introduce
regressions in existing cases when turned off (default for now), or
cause any significant maintaince burden.
The randomization is done on a best-effort basis - that is, the
allocator falls back to a first fit strategy if fragmentation prevents
entropy injection. It is trivial to implement a strong mode where
failure to guarantee the requested amount of entropy results in
mapping request failure, but I do not consider that to be usable.
I have not fine-tuned the amount of entropy injected right now. It is
only a quantitive change that will not change the implementation. The
current amount is controlled by aslr_pages_rnd.
To not spoil coalescing optimizations, to reduce the page table
fragmentation inherent to ASLR, and to keep the transient superpage
promotion for the malloced memory, locality clustering is implemented
for anonymous private mappings, which are automatically grouped until
fragmentation kicks in. The initial location for the anon group range
is, of course, randomized. This is controlled by vm.cluster_anon,
enabled by default.
The default mode keeps the sbrk area unpopulated by other mappings,
but this can be turned off, which gives much more breathing bits on
architectures with small address space, such as i386. This is tied
with the question of following an application's hint about the mmap(2)
base address. Testing shows that ignoring the hint does not affect the
function of common applications, but I would expect more demanding
code could break. By default sbrk is preserved and mmap hints are
satisfied, which can be changed by using the
kern.elf{32,64}.aslr.honor_sbrk sysctl.
ASLR is enabled on per-ABI basis, and currently it is only allowed on
FreeBSD native i386 and amd64 (including compat 32bit) ABIs. Support
for additional architectures will be added after further testing.
Both per-process and per-image controls are implemented:
- procctl(2) adds PROC_ASLR_CTL/PROC_ASLR_STATUS;
- NT_FREEBSD_FCTL_ASLR_DISABLE feature control note bit makes it possible
to force ASLR off for the given binary. (A tool to edit the feature
control note is in development.)
Global controls are:
- kern.elf{32,64}.aslr.enable - for non-fixed mappings done by mmap(2);
- kern.elf{32,64}.aslr.pie_enable - for PIE image activation mappings;
- kern.elf{32,64}.aslr.honor_sbrk - allow to use sbrk area for mmap(2);
- vm.cluster_anon - enables anon mapping clustering.
PR: 208580 (exp runs)
Exp-runs done by: antoine
Reviewed by: markj (previous version)
Discussed with: emaste
Tested by: pho
MFC after: 1 month
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D5603
2019-02-10 17:19:45 +00:00
|
|
|
case PROC_ASLR_CTL:
|
2019-07-02 19:07:17 +00:00
|
|
|
case PROC_PROTMAX_CTL:
|
2013-09-19 18:53:42 +00:00
|
|
|
case PROC_SPROTECT:
|
2015-01-18 15:13:11 +00:00
|
|
|
case PROC_TRACE_CTL:
|
2016-09-21 08:23:33 +00:00
|
|
|
case PROC_TRAPCAP_CTL:
|
2013-09-19 18:53:42 +00:00
|
|
|
error = copyin(PTRIN(uap->data), &flags, sizeof(flags));
|
2014-12-15 12:01:42 +00:00
|
|
|
if (error != 0)
|
2013-09-19 18:53:42 +00:00
|
|
|
return (error);
|
|
|
|
data = &flags;
|
|
|
|
break;
|
2014-12-15 12:01:42 +00:00
|
|
|
case PROC_REAP_ACQUIRE:
|
|
|
|
case PROC_REAP_RELEASE:
|
|
|
|
if (uap->data != NULL)
|
|
|
|
return (EINVAL);
|
|
|
|
data = NULL;
|
|
|
|
break;
|
|
|
|
case PROC_REAP_STATUS:
|
|
|
|
data = &x.rs;
|
|
|
|
break;
|
|
|
|
case PROC_REAP_GETPIDS:
|
|
|
|
error = copyin(uap->data, &x32.rp, sizeof(x32.rp));
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
CP(x32.rp, x.rp, rp_count);
|
|
|
|
PTRIN_CP(x32.rp, x.rp, rp_pids);
|
|
|
|
data = &x.rp;
|
|
|
|
break;
|
|
|
|
case PROC_REAP_KILL:
|
|
|
|
error = copyin(uap->data, &x.rk, sizeof(x.rk));
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
data = &x.rk;
|
|
|
|
break;
|
Implement Address Space Layout Randomization (ASLR)
With this change, randomization can be enabled for all non-fixed
mappings. It means that the base address for the mapping is selected
with a guaranteed amount of entropy (bits). If the mapping was
requested to be superpage aligned, the randomization honours the
superpage attributes.
Although the value of ASLR is diminshing over time as exploit authors
work out simple ASLR bypass techniques, it elimintates the trivial
exploitation of certain vulnerabilities, at least in theory. This
implementation is relatively small and happens at the correct
architectural level. Also, it is not expected to introduce
regressions in existing cases when turned off (default for now), or
cause any significant maintaince burden.
The randomization is done on a best-effort basis - that is, the
allocator falls back to a first fit strategy if fragmentation prevents
entropy injection. It is trivial to implement a strong mode where
failure to guarantee the requested amount of entropy results in
mapping request failure, but I do not consider that to be usable.
I have not fine-tuned the amount of entropy injected right now. It is
only a quantitive change that will not change the implementation. The
current amount is controlled by aslr_pages_rnd.
To not spoil coalescing optimizations, to reduce the page table
fragmentation inherent to ASLR, and to keep the transient superpage
promotion for the malloced memory, locality clustering is implemented
for anonymous private mappings, which are automatically grouped until
fragmentation kicks in. The initial location for the anon group range
is, of course, randomized. This is controlled by vm.cluster_anon,
enabled by default.
The default mode keeps the sbrk area unpopulated by other mappings,
but this can be turned off, which gives much more breathing bits on
architectures with small address space, such as i386. This is tied
with the question of following an application's hint about the mmap(2)
base address. Testing shows that ignoring the hint does not affect the
function of common applications, but I would expect more demanding
code could break. By default sbrk is preserved and mmap hints are
satisfied, which can be changed by using the
kern.elf{32,64}.aslr.honor_sbrk sysctl.
ASLR is enabled on per-ABI basis, and currently it is only allowed on
FreeBSD native i386 and amd64 (including compat 32bit) ABIs. Support
for additional architectures will be added after further testing.
Both per-process and per-image controls are implemented:
- procctl(2) adds PROC_ASLR_CTL/PROC_ASLR_STATUS;
- NT_FREEBSD_FCTL_ASLR_DISABLE feature control note bit makes it possible
to force ASLR off for the given binary. (A tool to edit the feature
control note is in development.)
Global controls are:
- kern.elf{32,64}.aslr.enable - for non-fixed mappings done by mmap(2);
- kern.elf{32,64}.aslr.pie_enable - for PIE image activation mappings;
- kern.elf{32,64}.aslr.honor_sbrk - allow to use sbrk area for mmap(2);
- vm.cluster_anon - enables anon mapping clustering.
PR: 208580 (exp runs)
Exp-runs done by: antoine
Reviewed by: markj (previous version)
Discussed with: emaste
Tested by: pho
MFC after: 1 month
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D5603
2019-02-10 17:19:45 +00:00
|
|
|
case PROC_ASLR_STATUS:
|
2019-07-02 19:07:17 +00:00
|
|
|
case PROC_PROTMAX_STATUS:
|
2015-01-18 15:13:11 +00:00
|
|
|
case PROC_TRACE_STATUS:
|
2016-09-21 08:23:33 +00:00
|
|
|
case PROC_TRAPCAP_STATUS:
|
2015-01-18 15:13:11 +00:00
|
|
|
data = &flags;
|
|
|
|
break;
|
2018-04-20 15:19:27 +00:00
|
|
|
case PROC_PDEATHSIG_CTL:
|
2018-04-18 21:31:13 +00:00
|
|
|
error = copyin(uap->data, &signum, sizeof(signum));
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
data = &signum;
|
|
|
|
break;
|
2018-04-20 15:19:27 +00:00
|
|
|
case PROC_PDEATHSIG_STATUS:
|
2018-04-18 21:31:13 +00:00
|
|
|
data = &signum;
|
|
|
|
break;
|
2013-09-19 18:53:42 +00:00
|
|
|
default:
|
|
|
|
return (EINVAL);
|
|
|
|
}
|
2014-12-15 12:01:42 +00:00
|
|
|
error = kern_procctl(td, uap->idtype, PAIR32TO64(id_t, uap->id),
|
|
|
|
uap->com, data);
|
|
|
|
switch (uap->com) {
|
|
|
|
case PROC_REAP_STATUS:
|
|
|
|
if (error == 0)
|
|
|
|
error = copyout(&x.rs, uap->data, sizeof(x.rs));
|
|
|
|
break;
|
|
|
|
case PROC_REAP_KILL:
|
|
|
|
error1 = copyout(&x.rk, uap->data, sizeof(x.rk));
|
|
|
|
if (error == 0)
|
|
|
|
error = error1;
|
|
|
|
break;
|
Implement Address Space Layout Randomization (ASLR)
With this change, randomization can be enabled for all non-fixed
mappings. It means that the base address for the mapping is selected
with a guaranteed amount of entropy (bits). If the mapping was
requested to be superpage aligned, the randomization honours the
superpage attributes.
Although the value of ASLR is diminshing over time as exploit authors
work out simple ASLR bypass techniques, it elimintates the trivial
exploitation of certain vulnerabilities, at least in theory. This
implementation is relatively small and happens at the correct
architectural level. Also, it is not expected to introduce
regressions in existing cases when turned off (default for now), or
cause any significant maintaince burden.
The randomization is done on a best-effort basis - that is, the
allocator falls back to a first fit strategy if fragmentation prevents
entropy injection. It is trivial to implement a strong mode where
failure to guarantee the requested amount of entropy results in
mapping request failure, but I do not consider that to be usable.
I have not fine-tuned the amount of entropy injected right now. It is
only a quantitive change that will not change the implementation. The
current amount is controlled by aslr_pages_rnd.
To not spoil coalescing optimizations, to reduce the page table
fragmentation inherent to ASLR, and to keep the transient superpage
promotion for the malloced memory, locality clustering is implemented
for anonymous private mappings, which are automatically grouped until
fragmentation kicks in. The initial location for the anon group range
is, of course, randomized. This is controlled by vm.cluster_anon,
enabled by default.
The default mode keeps the sbrk area unpopulated by other mappings,
but this can be turned off, which gives much more breathing bits on
architectures with small address space, such as i386. This is tied
with the question of following an application's hint about the mmap(2)
base address. Testing shows that ignoring the hint does not affect the
function of common applications, but I would expect more demanding
code could break. By default sbrk is preserved and mmap hints are
satisfied, which can be changed by using the
kern.elf{32,64}.aslr.honor_sbrk sysctl.
ASLR is enabled on per-ABI basis, and currently it is only allowed on
FreeBSD native i386 and amd64 (including compat 32bit) ABIs. Support
for additional architectures will be added after further testing.
Both per-process and per-image controls are implemented:
- procctl(2) adds PROC_ASLR_CTL/PROC_ASLR_STATUS;
- NT_FREEBSD_FCTL_ASLR_DISABLE feature control note bit makes it possible
to force ASLR off for the given binary. (A tool to edit the feature
control note is in development.)
Global controls are:
- kern.elf{32,64}.aslr.enable - for non-fixed mappings done by mmap(2);
- kern.elf{32,64}.aslr.pie_enable - for PIE image activation mappings;
- kern.elf{32,64}.aslr.honor_sbrk - allow to use sbrk area for mmap(2);
- vm.cluster_anon - enables anon mapping clustering.
PR: 208580 (exp runs)
Exp-runs done by: antoine
Reviewed by: markj (previous version)
Discussed with: emaste
Tested by: pho
MFC after: 1 month
Sponsored by: The FreeBSD Foundation
Differential revision: https://reviews.freebsd.org/D5603
2019-02-10 17:19:45 +00:00
|
|
|
case PROC_ASLR_STATUS:
|
2019-07-02 19:07:17 +00:00
|
|
|
case PROC_PROTMAX_STATUS:
|
2015-01-18 15:13:11 +00:00
|
|
|
case PROC_TRACE_STATUS:
|
2016-09-21 08:23:33 +00:00
|
|
|
case PROC_TRAPCAP_STATUS:
|
2015-01-18 15:13:11 +00:00
|
|
|
if (error == 0)
|
|
|
|
error = copyout(&flags, uap->data, sizeof(flags));
|
|
|
|
break;
|
2018-04-20 15:19:27 +00:00
|
|
|
case PROC_PDEATHSIG_STATUS:
|
2018-04-18 21:31:13 +00:00
|
|
|
if (error == 0)
|
|
|
|
error = copyout(&signum, uap->data, sizeof(signum));
|
|
|
|
break;
|
2014-12-15 12:01:42 +00:00
|
|
|
}
|
|
|
|
return (error);
|
2013-09-19 18:53:42 +00:00
|
|
|
}
|
2014-08-27 01:02:02 +00:00
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_fcntl(struct thread *td, struct freebsd32_fcntl_args *uap)
|
|
|
|
{
|
2014-09-25 21:07:19 +00:00
|
|
|
long tmp;
|
2014-08-27 01:02:02 +00:00
|
|
|
|
|
|
|
switch (uap->cmd) {
|
|
|
|
/*
|
|
|
|
* Do unsigned conversion for arg when operation
|
|
|
|
* interprets it as flags or pointer.
|
|
|
|
*/
|
|
|
|
case F_SETLK_REMOTE:
|
|
|
|
case F_SETLKW:
|
|
|
|
case F_SETLK:
|
|
|
|
case F_GETLK:
|
|
|
|
case F_SETFD:
|
|
|
|
case F_SETFL:
|
2015-01-15 10:43:58 +00:00
|
|
|
case F_OGETLK:
|
|
|
|
case F_OSETLK:
|
|
|
|
case F_OSETLKW:
|
2014-08-27 01:02:02 +00:00
|
|
|
tmp = (unsigned int)(uap->arg);
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
tmp = uap->arg;
|
|
|
|
break;
|
|
|
|
}
|
2014-09-25 21:07:19 +00:00
|
|
|
return (kern_fcntl_freebsd(td, uap->fd, uap->cmd, tmp));
|
2014-08-27 01:02:02 +00:00
|
|
|
}
|
2014-11-13 05:26:14 +00:00
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_ppoll(struct thread *td, struct freebsd32_ppoll_args *uap)
|
|
|
|
{
|
|
|
|
struct timespec32 ts32;
|
|
|
|
struct timespec ts, *tsp;
|
|
|
|
sigset_t set, *ssp;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
if (uap->ts != NULL) {
|
|
|
|
error = copyin(uap->ts, &ts32, sizeof(ts32));
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
CP(ts32, ts, tv_sec);
|
|
|
|
CP(ts32, ts, tv_nsec);
|
|
|
|
tsp = &ts;
|
|
|
|
} else
|
|
|
|
tsp = NULL;
|
|
|
|
if (uap->set != NULL) {
|
|
|
|
error = copyin(uap->set, &set, sizeof(set));
|
|
|
|
if (error != 0)
|
|
|
|
return (error);
|
|
|
|
ssp = &set;
|
|
|
|
} else
|
|
|
|
ssp = NULL;
|
|
|
|
|
|
|
|
return (kern_poll(td, uap->fds, uap->nfds, tsp, ssp));
|
|
|
|
}
|
2018-07-31 17:15:31 +00:00
|
|
|
|
|
|
|
int
|
|
|
|
freebsd32_sched_rr_get_interval(struct thread *td,
|
|
|
|
struct freebsd32_sched_rr_get_interval_args *uap)
|
|
|
|
{
|
|
|
|
struct timespec ts;
|
|
|
|
struct timespec32 ts32;
|
|
|
|
int error;
|
|
|
|
|
|
|
|
error = kern_sched_rr_get_interval(td, uap->pid, &ts);
|
|
|
|
if (error == 0) {
|
|
|
|
CP(ts, ts32, tv_sec);
|
|
|
|
CP(ts, ts32, tv_nsec);
|
|
|
|
error = copyout(&ts32, uap->interval, sizeof(ts32));
|
|
|
|
}
|
|
|
|
return (error);
|
|
|
|
}
|