19acbbeafSnn /*
29acbbeafSnn * CDDL HEADER START
39acbbeafSnn *
49acbbeafSnn * The contents of this file are subject to the terms of the
59acbbeafSnn * Common Development and Distribution License (the "License").
69acbbeafSnn * You may not use this file except in compliance with the License.
79acbbeafSnn *
89acbbeafSnn * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
99acbbeafSnn * or http://www.opensolaris.org/os/licensing.
109acbbeafSnn * See the License for the specific language governing permissions
119acbbeafSnn * and limitations under the License.
129acbbeafSnn *
139acbbeafSnn * When distributing Covered Code, include this CDDL HEADER in each
149acbbeafSnn * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
159acbbeafSnn * If applicable, add the following below this CDDL HEADER, with the
169acbbeafSnn * fields enclosed by brackets "[]" replaced with your own identifying
179acbbeafSnn * information: Portions Copyright [yyyy] [name of copyright owner]
189acbbeafSnn *
199acbbeafSnn * CDDL HEADER END
209acbbeafSnn */
21*794f0adbSRoger A. Faulkner
229acbbeafSnn /*
2380e2ca85S * Copyright (c) 2006, 2010, Oracle and/or its affiliates. All rights reserved.
249acbbeafSnn */
259acbbeafSnn
269acbbeafSnn #include <sys/errno.h>
279acbbeafSnn #include <sys/exec.h>
289acbbeafSnn #include <sys/kmem.h>
299acbbeafSnn #include <sys/modctl.h>
309acbbeafSnn #include <sys/model.h>
319acbbeafSnn #include <sys/proc.h>
329acbbeafSnn #include <sys/syscall.h>
339acbbeafSnn #include <sys/systm.h>
349acbbeafSnn #include <sys/thread.h>
359acbbeafSnn #include <sys/cmn_err.h>
369acbbeafSnn #include <sys/archsystm.h>
37628e3cbeSEdward Pilatowicz #include <sys/pathname.h>
389acbbeafSnn
399acbbeafSnn #include <sys/machbrand.h>
409acbbeafSnn #include <sys/brand.h>
419acbbeafSnn #include "sn1_brand.h"
429acbbeafSnn
439acbbeafSnn char *sn1_emulation_table = NULL;
449acbbeafSnn
45319378d9Seh void sn1_init_brand_data(zone_t *);
46319378d9Seh void sn1_free_brand_data(zone_t *);
479acbbeafSnn void sn1_setbrand(proc_t *);
489acbbeafSnn int sn1_getattr(zone_t *, int, void *, size_t *);
499acbbeafSnn int sn1_setattr(zone_t *, int, void *, size_t);
509acbbeafSnn int sn1_brandsys(int, int64_t *, uintptr_t, uintptr_t, uintptr_t,
519acbbeafSnn uintptr_t, uintptr_t, uintptr_t);
529acbbeafSnn void sn1_copy_procdata(proc_t *, proc_t *);
539acbbeafSnn void sn1_proc_exit(struct proc *, klwp_t *);
549acbbeafSnn void sn1_exec();
559acbbeafSnn int sn1_initlwp(klwp_t *);
569acbbeafSnn void sn1_forklwp(klwp_t *, klwp_t *);
579acbbeafSnn void sn1_freelwp(klwp_t *);
589acbbeafSnn void sn1_lwpexit(klwp_t *);
599acbbeafSnn int sn1_elfexec(vnode_t *, execa_t *, uarg_t *, intpdata_t *, int,
609acbbeafSnn long *, int, caddr_t, cred_t *, int);
619acbbeafSnn
629acbbeafSnn /* sn1 brand */
639acbbeafSnn struct brand_ops sn1_brops = {
64319378d9Seh sn1_init_brand_data,
65319378d9Seh sn1_free_brand_data,
669acbbeafSnn sn1_brandsys,
679acbbeafSnn sn1_setbrand,
689acbbeafSnn sn1_getattr,
699acbbeafSnn sn1_setattr,
709acbbeafSnn sn1_copy_procdata,
719acbbeafSnn sn1_proc_exit,
729acbbeafSnn sn1_exec,
739acbbeafSnn lwp_setrval,
749acbbeafSnn sn1_initlwp,
759acbbeafSnn sn1_forklwp,
769acbbeafSnn sn1_freelwp,
779acbbeafSnn sn1_lwpexit,
78eb9dbf0cSRoger A. Faulkner sn1_elfexec,
798f798d3aSRoger A. Faulkner NULL,
808f798d3aSRoger A. Faulkner NULL,
818f798d3aSRoger A. Faulkner NSIG,
829acbbeafSnn };
839acbbeafSnn
849acbbeafSnn #ifdef sparc
859acbbeafSnn
869acbbeafSnn struct brand_mach_ops sn1_mops = {
879acbbeafSnn sn1_brand_syscall_callback,
88628e3cbeSEdward Pilatowicz sn1_brand_syscall32_callback
899acbbeafSnn };
909acbbeafSnn
919acbbeafSnn #else /* sparc */
929acbbeafSnn
939acbbeafSnn #ifdef __amd64
949acbbeafSnn
959acbbeafSnn struct brand_mach_ops sn1_mops = {
969acbbeafSnn sn1_brand_sysenter_callback,
979acbbeafSnn sn1_brand_int91_callback,
989acbbeafSnn sn1_brand_syscall_callback,
99eb5a5c78SSurya Prakki sn1_brand_syscall32_callback
1009acbbeafSnn };
1019acbbeafSnn
1029acbbeafSnn #else /* ! __amd64 */
1039acbbeafSnn
1049acbbeafSnn struct brand_mach_ops sn1_mops = {
1059acbbeafSnn sn1_brand_sysenter_callback,
1069acbbeafSnn NULL,
1079acbbeafSnn sn1_brand_syscall_callback,
1089acbbeafSnn NULL
1099acbbeafSnn };
1109acbbeafSnn #endif /* __amd64 */
1119acbbeafSnn
1129acbbeafSnn #endif /* _sparc */
1139acbbeafSnn
1149acbbeafSnn struct brand sn1_brand = {
1159acbbeafSnn BRAND_VER_1,
1169acbbeafSnn "sn1",
1179acbbeafSnn &sn1_brops,
1189acbbeafSnn &sn1_mops
1199acbbeafSnn };
1209acbbeafSnn
1219acbbeafSnn static struct modlbrand modlbrand = {
122c6f42f0eSedp &mod_brandops, /* type of module */
123c6f42f0eSedp "Solaris N-1 Brand", /* description of module */
124c6f42f0eSedp &sn1_brand /* driver ops */
1259acbbeafSnn };
1269acbbeafSnn
1279acbbeafSnn static struct modlinkage modlinkage = {
1289acbbeafSnn MODREV_1, (void *)&modlbrand, NULL
1299acbbeafSnn };
1309acbbeafSnn
1319acbbeafSnn void
sn1_setbrand(proc_t * p)1329acbbeafSnn sn1_setbrand(proc_t *p)
1339acbbeafSnn {
13480e2ca85S brand_solaris_setbrand(p, &sn1_brand);
1359acbbeafSnn }
1369acbbeafSnn
1379acbbeafSnn /* ARGSUSED */
1389acbbeafSnn int
sn1_getattr(zone_t * zone,int attr,void * buf,size_t * bufsize)1399acbbeafSnn sn1_getattr(zone_t *zone, int attr, void *buf, size_t *bufsize)
1409acbbeafSnn {
1419acbbeafSnn return (EINVAL);
1429acbbeafSnn }
1439acbbeafSnn
1449acbbeafSnn /* ARGSUSED */
1459acbbeafSnn int
sn1_setattr(zone_t * zone,int attr,void * buf,size_t bufsize)1469acbbeafSnn sn1_setattr(zone_t *zone, int attr, void *buf, size_t bufsize)
1479acbbeafSnn {
1489acbbeafSnn return (EINVAL);
1499acbbeafSnn }
1509acbbeafSnn
1519acbbeafSnn /*ARGSUSED*/
1529acbbeafSnn int
sn1_brandsys(int cmd,int64_t * rval,uintptr_t arg1,uintptr_t arg2,uintptr_t arg3,uintptr_t arg4,uintptr_t arg5,uintptr_t arg6)1539acbbeafSnn sn1_brandsys(int cmd, int64_t *rval, uintptr_t arg1, uintptr_t arg2,
1549acbbeafSnn uintptr_t arg3, uintptr_t arg4, uintptr_t arg5, uintptr_t arg6)
1559acbbeafSnn {
15680e2ca85S int res;
157628e3cbeSEdward Pilatowicz
1589acbbeafSnn *rval = 0;
1599acbbeafSnn
16080e2ca85S res = brand_solaris_cmd(cmd, arg1, arg2, arg3, &sn1_brand, SN1_VERSION);
16180e2ca85S if (res >= 0)
16280e2ca85S return (res);
1639acbbeafSnn
1649acbbeafSnn return (EINVAL);
1659acbbeafSnn }
1669acbbeafSnn
1679acbbeafSnn void
sn1_copy_procdata(proc_t * child,proc_t * parent)1689acbbeafSnn sn1_copy_procdata(proc_t *child, proc_t *parent)
1699acbbeafSnn {
17080e2ca85S brand_solaris_copy_procdata(child, parent, &sn1_brand);
1719acbbeafSnn }
1729acbbeafSnn
1739acbbeafSnn void
sn1_proc_exit(struct proc * p,klwp_t * l)1749acbbeafSnn sn1_proc_exit(struct proc *p, klwp_t *l)
1759acbbeafSnn {
17680e2ca85S brand_solaris_proc_exit(p, l, &sn1_brand);
1779acbbeafSnn }
1789acbbeafSnn
1799acbbeafSnn void
sn1_exec()1809acbbeafSnn sn1_exec()
1819acbbeafSnn {
18280e2ca85S brand_solaris_exec(&sn1_brand);
1839acbbeafSnn }
1849acbbeafSnn
1859acbbeafSnn int
sn1_initlwp(klwp_t * l)1869acbbeafSnn sn1_initlwp(klwp_t *l)
1879acbbeafSnn {
18880e2ca85S return (brand_solaris_initlwp(l, &sn1_brand));
1899acbbeafSnn }
1909acbbeafSnn
191319378d9Seh void
sn1_forklwp(klwp_t * p,klwp_t * c)192fd9e7635Sedp sn1_forklwp(klwp_t *p, klwp_t *c)
193319378d9Seh {
19480e2ca85S brand_solaris_forklwp(p, c, &sn1_brand);
195319378d9Seh }
196319378d9Seh
197319378d9Seh void
sn1_freelwp(klwp_t * l)198fd9e7635Sedp sn1_freelwp(klwp_t *l)
199319378d9Seh {
20080e2ca85S brand_solaris_freelwp(l, &sn1_brand);
201319378d9Seh }
202319378d9Seh
2039acbbeafSnn void
sn1_lwpexit(klwp_t * l)204fd9e7635Sedp sn1_lwpexit(klwp_t *l)
2059acbbeafSnn {
20680e2ca85S brand_solaris_lwpexit(l, &sn1_brand);
2079acbbeafSnn }
2089acbbeafSnn
2099acbbeafSnn /*ARGSUSED*/
2109acbbeafSnn void
sn1_free_brand_data(zone_t * zone)211628e3cbeSEdward Pilatowicz sn1_free_brand_data(zone_t *zone)
2129acbbeafSnn {
2139acbbeafSnn }
2149acbbeafSnn
2159acbbeafSnn /*ARGSUSED*/
2169acbbeafSnn void
sn1_init_brand_data(zone_t * zone)217628e3cbeSEdward Pilatowicz sn1_init_brand_data(zone_t *zone)
218628e3cbeSEdward Pilatowicz {
219628e3cbeSEdward Pilatowicz }
220628e3cbeSEdward Pilatowicz
2219acbbeafSnn int
sn1_elfexec(vnode_t * vp,execa_t * uap,uarg_t * args,intpdata_t * idatap,int level,long * execsz,int setid,caddr_t exec_file,cred_t * cred,int brand_action)2229acbbeafSnn sn1_elfexec(vnode_t *vp, execa_t *uap, uarg_t *args, intpdata_t *idatap,
2239acbbeafSnn int level, long *execsz, int setid, caddr_t exec_file, cred_t *cred,
2249acbbeafSnn int brand_action)
2259acbbeafSnn {
22680e2ca85S return (brand_solaris_elfexec(vp, uap, args, idatap, level, execsz,
22780e2ca85S setid, exec_file, cred, brand_action, &sn1_brand, SN1_BRANDNAME,
22880e2ca85S SN1_LIB, SN1_LIB32, SN1_LINKER, SN1_LINKER32));
2299acbbeafSnn }
2309acbbeafSnn
2319acbbeafSnn int
_init(void)2329acbbeafSnn _init(void)
2339acbbeafSnn {
2349acbbeafSnn int err;
2359acbbeafSnn
2369acbbeafSnn /*
2379acbbeafSnn * Set up the table indicating which system calls we want to
2389acbbeafSnn * interpose on. We should probably build this automatically from
2399acbbeafSnn * a list of system calls that is shared with the user-space
2409acbbeafSnn * library.
2419acbbeafSnn */
2429acbbeafSnn sn1_emulation_table = kmem_zalloc(NSYSCALL, KM_SLEEP);
243628e3cbeSEdward Pilatowicz sn1_emulation_table[SYS_read] = 1; /* 3 */
244628e3cbeSEdward Pilatowicz sn1_emulation_table[SYS_write] = 1; /* 4 */
245628e3cbeSEdward Pilatowicz sn1_emulation_table[SYS_time] = 1; /* 13 */
246628e3cbeSEdward Pilatowicz sn1_emulation_table[SYS_getpid] = 1; /* 20 */
247628e3cbeSEdward Pilatowicz sn1_emulation_table[SYS_mount] = 1; /* 21 */
248628e3cbeSEdward Pilatowicz sn1_emulation_table[SYS_getuid] = 1; /* 24 */
249628e3cbeSEdward Pilatowicz sn1_emulation_table[SYS_times] = 1; /* 43 */
250628e3cbeSEdward Pilatowicz sn1_emulation_table[SYS_getgid] = 1; /* 47 */
251628e3cbeSEdward Pilatowicz sn1_emulation_table[SYS_utssys] = 1; /* 57 */
2528fd04b83SRoger A. Faulkner sn1_emulation_table[SYS_waitid] = 1; /* 107 */
253628e3cbeSEdward Pilatowicz sn1_emulation_table[SYS_uname] = 1; /* 135 */
2549acbbeafSnn
2559acbbeafSnn err = mod_install(&modlinkage);
2569acbbeafSnn if (err) {
2579acbbeafSnn cmn_err(CE_WARN, "Couldn't install brand module");
2589acbbeafSnn kmem_free(sn1_emulation_table, NSYSCALL);
2599acbbeafSnn }
2609acbbeafSnn
2619acbbeafSnn return (err);
2629acbbeafSnn }
2639acbbeafSnn
2649acbbeafSnn int
_info(struct modinfo * modinfop)2659acbbeafSnn _info(struct modinfo *modinfop)
2669acbbeafSnn {
2679acbbeafSnn return (mod_info(&modlinkage, modinfop));
2689acbbeafSnn }
2699acbbeafSnn
2709acbbeafSnn int
_fini(void)2719acbbeafSnn _fini(void)
2729acbbeafSnn {
27380e2ca85S return (brand_solaris_fini(&sn1_emulation_table, &modlinkage,
27480e2ca85S &sn1_brand));
2759acbbeafSnn }
276