1 /* $Id: misc.c,v 1.36 2002/02/09 19:49:31 davem Exp $
2 * misc.c: Miscellaneous syscall emulation for Solaris
4 * Copyright (C) 1997,1998 Jakub Jelinek (jj@sunsite.mff.cuni.cz)
7 #include <linux/module.h>
8 #include <linux/types.h>
9 #include <linux/utsname.h>
10 #include <linux/limits.h>
12 #include <linux/smp.h>
13 #include <linux/tty.h>
14 #include <linux/mman.h>
15 #include <linux/file.h>
16 #include <linux/timex.h>
17 #include <linux/major.h>
18 #include <linux/compat.h>
20 #include <asm/uaccess.h>
21 #include <asm/string.h>
22 #include <asm/oplib.h>
23 #include <asm/idprom.h>
29 /* Conversion from Linux to Solaris errnos. 0-34 are identity mapped.
30 Some Linux errnos (EPROCLIM, EDOTDOT, ERREMOTE, EUCLEAN, ENOTNAM,
31 ENAVAIL, EISNAM, EREMOTEIO, ENOMEDIUM, EMEDIUMTYPE) have no Solaris
32 equivalents. I return EINVAL in that case, which is very wrong. If
33 someone suggest a better value for them, you're welcomed.
34 On the other side, Solaris ECANCELED and ENOTSUP have no Linux equivalents,
35 but that doesn't matter here. --jj */
36 int solaris_err_table
[] = {
37 /* 0 */ 0, 1, 2, 3, 4, 5, 6, 7, 8, 9,
38 /* 10 */ 10, 11, 12, 13, 14, 15, 16, 17, 18, 19,
39 /* 20 */ 20, 21, 22, 23, 24, 25, 26, 27, 28, 29,
40 /* 30 */ 30, 31, 32, 33, 34, 22, 150, 149, 95, 96,
41 /* 40 */ 97, 98, 99, 120, 121, 122, 123, 124, 125, 126,
42 /* 50 */ 127, 128, 129, 130, 131, 132, 133, 134, 143, 144,
43 /* 60 */ 145, 146, 90, 78, 147, 148, 93, 22, 94, 49,
44 /* 70 */ 151, 66, 60, 62, 63, 35, 77, 36, 45, 46,
45 /* 80 */ 64, 22, 67, 68, 69, 70, 71, 74, 22, 82,
46 /* 90 */ 89, 92, 79, 81, 37, 38, 39, 40, 41, 42,
47 /* 100 */ 43, 44, 50, 51, 52, 53, 54, 55, 56, 57,
48 /* 110 */ 87, 61, 84, 65, 83, 80, 91, 22, 22, 22,
49 /* 120 */ 22, 22, 88, 86, 85, 22, 22,
52 #define SOLARIS_NR_OPEN 256
54 static u32
do_solaris_mmap(u32 addr
, u32 len
, u32 prot
, u32 flags
, u32 fd
, u64 off
)
56 struct file
*file
= NULL
;
57 unsigned long retval
, ret_type
;
59 /* Do we need it here? */
60 set_personality(PER_SVR4
);
61 if (flags
& MAP_NORESERVE
) {
65 printk("%s: unimplemented Solaris MAP_NORESERVE mmap() flag\n",
69 flags
&= ~MAP_NORESERVE
;
72 if(!(flags
& MAP_ANONYMOUS
)) {
73 if(fd
>= SOLARIS_NR_OPEN
)
79 struct inode
* inode
= file
->f_path
.dentry
->d_inode
;
80 if(imajor(inode
) == MEM_MAJOR
&&
82 flags
|= MAP_ANONYMOUS
;
90 len
= PAGE_ALIGN(len
);
91 if(!(flags
& MAP_FIXED
))
93 else if (len
> STACK_TOP32
|| addr
> STACK_TOP32
- len
)
95 ret_type
= flags
& _MAP_NEW
;
98 down_write(¤t
->mm
->mmap_sem
);
99 flags
&= ~(MAP_EXECUTABLE
| MAP_DENYWRITE
);
100 retval
= do_mmap(file
,
101 (unsigned long) addr
, (unsigned long) len
,
102 (unsigned long) prot
, (unsigned long) flags
, off
);
103 up_write(¤t
->mm
->mmap_sem
);
105 retval
= ((retval
< STACK_TOP32
) ? 0 : retval
);
114 asmlinkage u32
solaris_mmap(u32 addr
, u32 len
, u32 prot
, u32 flags
, u32 fd
, u32 off
)
116 return do_solaris_mmap(addr
, len
, prot
, flags
, fd
, (u64
) off
);
119 asmlinkage u32
solaris_mmap64(struct pt_regs
*regs
, u32 len
, u32 prot
, u32 flags
, u32 fd
, u32 offhi
)
123 if (regs
->u_regs
[UREG_G1
]) {
124 if (get_user (offlo
, (u32 __user
*)(long)((u32
)regs
->u_regs
[UREG_I6
] + 0x5c)))
127 if (get_user (offlo
, (u32 __user
*)(long)((u32
)regs
->u_regs
[UREG_I6
] + 0x60)))
130 return do_solaris_mmap((u32
)regs
->u_regs
[UREG_I0
], len
, prot
, flags
, fd
, (((u64
)offhi
)<<32)|offlo
);
133 asmlinkage
int solaris_brk(u32 brk
)
135 int (*sunos_brk
)(u32
) = (int (*)(u32
))SUNOS(17);
137 return sunos_brk(brk
);
140 static int __set_utsfield(char __user
*to
, int to_size
,
141 const char *from
, int from_size
,
142 int dotchop
, int countfrom
)
144 int len
= countfrom
? (to_size
> from_size
?
145 from_size
: to_size
) : to_size
;
148 if (copy_to_user(to
, from
, len
))
151 off
= len
< to_size
? len
: len
- 1;
153 const char *p
= strnchr(from
, len
, '.');
154 if (p
) off
= p
- from
;
157 if (__put_user('\0', to
+ off
))
163 #define set_utsfield(to, from, dotchop, countfrom) \
164 __set_utsfield((to), sizeof(to), \
165 (from), sizeof(from), \
166 (dotchop), (countfrom))
184 static char *machine(void)
186 switch (sparc_cpu_model
) {
187 case sun4
: return "sun4";
188 case sun4c
: return "sun4c";
189 case sun4e
: return "sun4e";
190 case sun4m
: return "sun4m";
191 case sun4d
: return "sun4d";
192 case sun4u
: return "sun4u";
193 default: return "sparc";
197 static char *platform(char *buffer
, int sz
)
199 struct device_node
*dp
= of_find_node_by_path("/");
203 len
= strlen(dp
->name
);
206 memcpy(buffer
, dp
->name
, len
);
211 for (p
= buffer
; *p
; p
++)
212 if (*p
== '/' || *p
== ' ') *p
= '_';
219 static char *serial(char *buffer
, int sz
)
221 struct device_node
*dp
= of_find_node_by_path("/options");
227 of_get_property(dp
, "system-board-serial#", &len
);
229 if (val
&& len
> 0) {
232 memcpy(buffer
, val
, len
);
237 return "4512348717234";
242 asmlinkage
int solaris_utssys(u32 buf
, u32 flags
, int which
, u32 buf2
)
244 struct sol_uname __user
*v
= A(buf
);
248 case 0: /* old uname */
250 err
= set_utsfield(v
->sysname
, "SunOS", 1, 0);
252 err
|= set_utsfield(v
->nodename
, utsname()->nodename
,
255 err
|= set_utsfield(v
->release
, "2.6", 0, 0);
256 err
|= set_utsfield(v
->version
, "Generic", 0, 0);
257 err
|= set_utsfield(v
->machine
, machine(), 0, 0);
258 return (err
? -EFAULT
: 0);
268 asmlinkage
int solaris_utsname(u32 buf
)
270 struct sol_utsname __user
*v
= A(buf
);
273 /* Why should we not lie a bit? */
275 err
= set_utsfield(v
->sysname
, "SunOS", 0, 0);
276 err
|= set_utsfield(v
->nodename
, utsname()->nodename
, 1, 1);
277 err
|= set_utsfield(v
->release
, "5.6", 0, 0);
278 err
|= set_utsfield(v
->version
, "Generic", 0, 0);
279 err
|= set_utsfield(v
->machine
, machine(), 0, 0);
282 return (err
? -EFAULT
: 0);
285 #define SI_SYSNAME 1 /* return name of operating system */
286 #define SI_HOSTNAME 2 /* return name of node */
287 #define SI_RELEASE 3 /* return release of operating system */
288 #define SI_VERSION 4 /* return version field of utsname */
289 #define SI_MACHINE 5 /* return kind of machine */
290 #define SI_ARCHITECTURE 6 /* return instruction set arch */
291 #define SI_HW_SERIAL 7 /* return hardware serial number */
292 #define SI_HW_PROVIDER 8 /* return hardware manufacturer */
293 #define SI_SRPC_DOMAIN 9 /* return secure RPC domain */
294 #define SI_PLATFORM 513 /* return platform identifier */
296 asmlinkage
int solaris_sysinfo(int cmd
, u32 buf
, s32 count
)
302 /* Again, we cheat :)) */
304 case SI_SYSNAME
: r
= "SunOS"; break;
308 for (p
= utsname()->nodename
, q
= buffer
;
309 q
< r
&& *p
&& *p
!= '.'; *q
++ = *p
++);
314 case SI_RELEASE
: r
= "5.6"; break;
315 case SI_MACHINE
: r
= machine(); break;
316 case SI_ARCHITECTURE
: r
= "sparc"; break;
317 case SI_HW_PROVIDER
: r
= "Sun_Microsystems"; break;
318 case SI_HW_SERIAL
: r
= serial(buffer
, sizeof(buffer
)); break;
319 case SI_PLATFORM
: r
= platform(buffer
, sizeof(buffer
)); break;
320 case SI_SRPC_DOMAIN
: r
= ""; break;
321 case SI_VERSION
: r
= "Generic"; break;
322 default: return -EINVAL
;
326 if (copy_to_user(A(buf
), r
, count
- 1) ||
327 __put_user(0, (char __user
*)A(buf
) + count
- 1))
330 if (copy_to_user(A(buf
), r
, len
))
336 #define SOLARIS_CONFIG_NGROUPS 2
337 #define SOLARIS_CONFIG_CHILD_MAX 3
338 #define SOLARIS_CONFIG_OPEN_FILES 4
339 #define SOLARIS_CONFIG_POSIX_VER 5
340 #define SOLARIS_CONFIG_PAGESIZE 6
341 #define SOLARIS_CONFIG_CLK_TCK 7
342 #define SOLARIS_CONFIG_XOPEN_VER 8
343 #define SOLARIS_CONFIG_PROF_TCK 10
344 #define SOLARIS_CONFIG_NPROC_CONF 11
345 #define SOLARIS_CONFIG_NPROC_ONLN 12
346 #define SOLARIS_CONFIG_AIO_LISTIO_MAX 13
347 #define SOLARIS_CONFIG_AIO_MAX 14
348 #define SOLARIS_CONFIG_AIO_PRIO_DELTA_MAX 15
349 #define SOLARIS_CONFIG_DELAYTIMER_MAX 16
350 #define SOLARIS_CONFIG_MQ_OPEN_MAX 17
351 #define SOLARIS_CONFIG_MQ_PRIO_MAX 18
352 #define SOLARIS_CONFIG_RTSIG_MAX 19
353 #define SOLARIS_CONFIG_SEM_NSEMS_MAX 20
354 #define SOLARIS_CONFIG_SEM_VALUE_MAX 21
355 #define SOLARIS_CONFIG_SIGQUEUE_MAX 22
356 #define SOLARIS_CONFIG_SIGRT_MIN 23
357 #define SOLARIS_CONFIG_SIGRT_MAX 24
358 #define SOLARIS_CONFIG_TIMER_MAX 25
359 #define SOLARIS_CONFIG_PHYS_PAGES 26
360 #define SOLARIS_CONFIG_AVPHYS_PAGES 27
362 asmlinkage
int solaris_sysconf(int id
)
365 case SOLARIS_CONFIG_NGROUPS
: return NGROUPS_MAX
;
366 case SOLARIS_CONFIG_CHILD_MAX
:
367 return current
->signal
->rlim
[RLIMIT_NPROC
].rlim_cur
;
368 case SOLARIS_CONFIG_OPEN_FILES
:
369 return current
->signal
->rlim
[RLIMIT_NOFILE
].rlim_cur
;
370 case SOLARIS_CONFIG_POSIX_VER
: return 199309;
371 case SOLARIS_CONFIG_PAGESIZE
: return PAGE_SIZE
;
372 case SOLARIS_CONFIG_XOPEN_VER
: return 3;
373 case SOLARIS_CONFIG_CLK_TCK
:
374 case SOLARIS_CONFIG_PROF_TCK
:
375 return sparc64_get_clock_tick(smp_processor_id());
377 case SOLARIS_CONFIG_NPROC_CONF
: return NR_CPUS
;
378 case SOLARIS_CONFIG_NPROC_ONLN
: return num_online_cpus();
380 case SOLARIS_CONFIG_NPROC_CONF
: return 1;
381 case SOLARIS_CONFIG_NPROC_ONLN
: return 1;
383 case SOLARIS_CONFIG_SIGRT_MIN
: return 37;
384 case SOLARIS_CONFIG_SIGRT_MAX
: return 44;
385 case SOLARIS_CONFIG_PHYS_PAGES
:
386 case SOLARIS_CONFIG_AVPHYS_PAGES
:
391 if (id
== SOLARIS_CONFIG_PHYS_PAGES
)
392 return s
.totalram
>>= PAGE_SHIFT
;
394 return s
.freeram
>>= PAGE_SHIFT
;
396 /* XXX support these as well -jj */
397 case SOLARIS_CONFIG_AIO_LISTIO_MAX
: return -EINVAL
;
398 case SOLARIS_CONFIG_AIO_MAX
: return -EINVAL
;
399 case SOLARIS_CONFIG_AIO_PRIO_DELTA_MAX
: return -EINVAL
;
400 case SOLARIS_CONFIG_DELAYTIMER_MAX
: return -EINVAL
;
401 case SOLARIS_CONFIG_MQ_OPEN_MAX
: return -EINVAL
;
402 case SOLARIS_CONFIG_MQ_PRIO_MAX
: return -EINVAL
;
403 case SOLARIS_CONFIG_RTSIG_MAX
: return -EINVAL
;
404 case SOLARIS_CONFIG_SEM_NSEMS_MAX
: return -EINVAL
;
405 case SOLARIS_CONFIG_SEM_VALUE_MAX
: return -EINVAL
;
406 case SOLARIS_CONFIG_SIGQUEUE_MAX
: return -EINVAL
;
407 case SOLARIS_CONFIG_TIMER_MAX
: return -EINVAL
;
408 default: return -EINVAL
;
412 asmlinkage
int solaris_procids(int cmd
, s32 pid
, s32 pgid
)
417 case 0: /* getpgrp */
418 return task_pgrp_nr(current
);
419 case 1: /* setpgrp */
421 int (*sys_setpgid
)(pid_t
,pid_t
) =
422 (int (*)(pid_t
,pid_t
))SYS(setpgid
);
424 /* can anyone explain me the difference between
425 Solaris setpgrp and setsid? */
426 ret
= sys_setpgid(0, 0);
428 proc_clear_tty(current
);
429 return task_pgrp_nr(current
);
433 int (*sys_getsid
)(pid_t
) = (int (*)(pid_t
))SYS(getsid
);
434 return sys_getsid(pid
);
438 int (*sys_setsid
)(void) = (int (*)(void))SYS(setsid
);
441 case 4: /* getpgid */
443 int (*sys_getpgid
)(pid_t
) = (int (*)(pid_t
))SYS(getpgid
);
444 return sys_getpgid(pid
);
446 case 5: /* setpgid */
448 int (*sys_setpgid
)(pid_t
,pid_t
) =
449 (int (*)(pid_t
,pid_t
))SYS(setpgid
);
450 return sys_setpgid(pid
,pgid
);
456 asmlinkage
int solaris_gettimeofday(u32 tim
)
458 int (*sys_gettimeofday
)(struct timeval
*, struct timezone
*) =
459 (int (*)(struct timeval
*, struct timezone
*))SYS(gettimeofday
);
461 return sys_gettimeofday((struct timeval
*)(u64
)tim
, NULL
);
464 #define RLIM_SOL_INFINITY32 0x7fffffff
465 #define RLIM_SOL_SAVED_MAX32 0x7ffffffe
466 #define RLIM_SOL_SAVED_CUR32 0x7ffffffd
467 #define RLIM_SOL_INFINITY ((u64)-3)
468 #define RLIM_SOL_SAVED_MAX ((u64)-2)
469 #define RLIM_SOL_SAVED_CUR ((u64)-1)
470 #define RESOURCE32(x) ((x > RLIM_INFINITY32) ? RLIM_INFINITY32 : x)
471 #define RLIMIT_SOL_NOFILE 5
472 #define RLIMIT_SOL_VMEM 6
479 asmlinkage
int solaris_getrlimit(unsigned int resource
, struct rlimit32 __user
*rlim
)
483 mm_segment_t old_fs
= get_fs ();
484 int (*sys_getrlimit
)(unsigned int, struct rlimit
*) =
485 (int (*)(unsigned int, struct rlimit
*))SYS(getrlimit
);
487 if (resource
> RLIMIT_SOL_VMEM
)
490 case RLIMIT_SOL_NOFILE
: resource
= RLIMIT_NOFILE
; break;
491 case RLIMIT_SOL_VMEM
: resource
= RLIMIT_AS
; break;
495 ret
= sys_getrlimit(resource
, &r
);
498 if (r
.rlim_cur
== RLIM_INFINITY
)
499 r
.rlim_cur
= RLIM_SOL_INFINITY32
;
500 else if ((u64
)r
.rlim_cur
> RLIM_SOL_INFINITY32
)
501 r
.rlim_cur
= RLIM_SOL_SAVED_CUR32
;
502 if (r
.rlim_max
== RLIM_INFINITY
)
503 r
.rlim_max
= RLIM_SOL_INFINITY32
;
504 else if ((u64
)r
.rlim_max
> RLIM_SOL_INFINITY32
)
505 r
.rlim_max
= RLIM_SOL_SAVED_MAX32
;
506 ret
= put_user (r
.rlim_cur
, &rlim
->rlim_cur
);
507 ret
|= __put_user (r
.rlim_max
, &rlim
->rlim_max
);
512 asmlinkage
int solaris_setrlimit(unsigned int resource
, struct rlimit32 __user
*rlim
)
514 struct rlimit r
, rold
;
516 mm_segment_t old_fs
= get_fs ();
517 int (*sys_getrlimit
)(unsigned int, struct rlimit __user
*) =
518 (int (*)(unsigned int, struct rlimit __user
*))SYS(getrlimit
);
519 int (*sys_setrlimit
)(unsigned int, struct rlimit __user
*) =
520 (int (*)(unsigned int, struct rlimit __user
*))SYS(setrlimit
);
522 if (resource
> RLIMIT_SOL_VMEM
)
525 case RLIMIT_SOL_NOFILE
: resource
= RLIMIT_NOFILE
; break;
526 case RLIMIT_SOL_VMEM
: resource
= RLIMIT_AS
; break;
529 if (get_user (r
.rlim_cur
, &rlim
->rlim_cur
) ||
530 __get_user (r
.rlim_max
, &rlim
->rlim_max
))
533 ret
= sys_getrlimit(resource
, &rold
);
535 if (r
.rlim_cur
== RLIM_SOL_INFINITY32
)
536 r
.rlim_cur
= RLIM_INFINITY
;
537 else if (r
.rlim_cur
== RLIM_SOL_SAVED_CUR32
)
538 r
.rlim_cur
= rold
.rlim_cur
;
539 else if (r
.rlim_cur
== RLIM_SOL_SAVED_MAX32
)
540 r
.rlim_cur
= rold
.rlim_max
;
541 if (r
.rlim_max
== RLIM_SOL_INFINITY32
)
542 r
.rlim_max
= RLIM_INFINITY
;
543 else if (r
.rlim_max
== RLIM_SOL_SAVED_CUR32
)
544 r
.rlim_max
= rold
.rlim_cur
;
545 else if (r
.rlim_max
== RLIM_SOL_SAVED_MAX32
)
546 r
.rlim_max
= rold
.rlim_max
;
547 ret
= sys_setrlimit(resource
, &r
);
553 asmlinkage
int solaris_getrlimit64(unsigned int resource
, struct rlimit __user
*rlim
)
557 mm_segment_t old_fs
= get_fs ();
558 int (*sys_getrlimit
)(unsigned int, struct rlimit __user
*) =
559 (int (*)(unsigned int, struct rlimit __user
*))SYS(getrlimit
);
561 if (resource
> RLIMIT_SOL_VMEM
)
564 case RLIMIT_SOL_NOFILE
: resource
= RLIMIT_NOFILE
; break;
565 case RLIMIT_SOL_VMEM
: resource
= RLIMIT_AS
; break;
569 ret
= sys_getrlimit(resource
, &r
);
572 if (r
.rlim_cur
== RLIM_INFINITY
)
573 r
.rlim_cur
= RLIM_SOL_INFINITY
;
574 if (r
.rlim_max
== RLIM_INFINITY
)
575 r
.rlim_max
= RLIM_SOL_INFINITY
;
576 ret
= put_user (r
.rlim_cur
, &rlim
->rlim_cur
);
577 ret
|= __put_user (r
.rlim_max
, &rlim
->rlim_max
);
582 asmlinkage
int solaris_setrlimit64(unsigned int resource
, struct rlimit __user
*rlim
)
584 struct rlimit r
, rold
;
586 mm_segment_t old_fs
= get_fs ();
587 int (*sys_getrlimit
)(unsigned int, struct rlimit __user
*) =
588 (int (*)(unsigned int, struct rlimit __user
*))SYS(getrlimit
);
589 int (*sys_setrlimit
)(unsigned int, struct rlimit __user
*) =
590 (int (*)(unsigned int, struct rlimit __user
*))SYS(setrlimit
);
592 if (resource
> RLIMIT_SOL_VMEM
)
595 case RLIMIT_SOL_NOFILE
: resource
= RLIMIT_NOFILE
; break;
596 case RLIMIT_SOL_VMEM
: resource
= RLIMIT_AS
; break;
599 if (get_user (r
.rlim_cur
, &rlim
->rlim_cur
) ||
600 __get_user (r
.rlim_max
, &rlim
->rlim_max
))
603 ret
= sys_getrlimit(resource
, &rold
);
605 if (r
.rlim_cur
== RLIM_SOL_INFINITY
)
606 r
.rlim_cur
= RLIM_INFINITY
;
607 else if (r
.rlim_cur
== RLIM_SOL_SAVED_CUR
)
608 r
.rlim_cur
= rold
.rlim_cur
;
609 else if (r
.rlim_cur
== RLIM_SOL_SAVED_MAX
)
610 r
.rlim_cur
= rold
.rlim_max
;
611 if (r
.rlim_max
== RLIM_SOL_INFINITY
)
612 r
.rlim_max
= RLIM_INFINITY
;
613 else if (r
.rlim_max
== RLIM_SOL_SAVED_CUR
)
614 r
.rlim_max
= rold
.rlim_cur
;
615 else if (r
.rlim_max
== RLIM_SOL_SAVED_MAX
)
616 r
.rlim_max
= rold
.rlim_max
;
617 ret
= sys_setrlimit(resource
, &r
);
623 struct sol_ntptimeval
{
624 struct compat_timeval time
;
649 asmlinkage
int solaris_ntp_gettime(struct sol_ntptimeval __user
*ntp
)
651 int (*sys_adjtimex
)(struct timex __user
*) =
652 (int (*)(struct timex __user
*))SYS(adjtimex
);
655 mm_segment_t old_fs
= get_fs();
659 ret
= sys_adjtimex(&t
);
663 ret
= put_user (t
.time
.tv_sec
, &ntp
->time
.tv_sec
);
664 ret
|= __put_user (t
.time
.tv_usec
, &ntp
->time
.tv_usec
);
665 ret
|= __put_user (t
.maxerror
, &ntp
->maxerror
);
666 ret
|= __put_user (t
.esterror
, &ntp
->esterror
);
670 asmlinkage
int solaris_ntp_adjtime(struct sol_timex __user
*txp
)
672 int (*sys_adjtimex
)(struct timex __user
*) =
673 (int (*)(struct timex __user
*))SYS(adjtimex
);
676 mm_segment_t old_fs
= get_fs();
678 ret
= get_user (t
.modes
, &txp
->modes
);
679 ret
|= __get_user (t
.offset
, &txp
->offset
);
680 ret
|= __get_user (t
.freq
, &txp
->freq
);
681 ret
|= __get_user (t
.maxerror
, &txp
->maxerror
);
682 ret
|= __get_user (t
.esterror
, &txp
->esterror
);
683 ret
|= __get_user (t
.status
, &txp
->status
);
684 ret
|= __get_user (t
.constant
, &txp
->constant
);
686 ret
= sys_adjtimex(&t
);
690 err
= put_user (t
.offset
, &txp
->offset
);
691 err
|= __put_user (t
.freq
, &txp
->freq
);
692 err
|= __put_user (t
.maxerror
, &txp
->maxerror
);
693 err
|= __put_user (t
.esterror
, &txp
->esterror
);
694 err
|= __put_user (t
.status
, &txp
->status
);
695 err
|= __put_user (t
.constant
, &txp
->constant
);
696 err
|= __put_user (t
.precision
, &txp
->precision
);
697 err
|= __put_user (t
.tolerance
, &txp
->tolerance
);
698 err
|= __put_user (t
.ppsfreq
, &txp
->ppsfreq
);
699 err
|= __put_user (t
.jitter
, &txp
->jitter
);
700 err
|= __put_user (t
.shift
, &txp
->shift
);
701 err
|= __put_user (t
.stabil
, &txp
->stabil
);
702 err
|= __put_user (t
.jitcnt
, &txp
->jitcnt
);
703 err
|= __put_user (t
.calcnt
, &txp
->calcnt
);
704 err
|= __put_user (t
.errcnt
, &txp
->errcnt
);
705 err
|= __put_user (t
.stbcnt
, &txp
->stbcnt
);
711 asmlinkage
int do_sol_unimplemented(struct pt_regs
*regs
)
713 printk ("Unimplemented Solaris syscall %d %08x %08x %08x %08x\n",
714 (int)regs
->u_regs
[UREG_G1
],
715 (int)regs
->u_regs
[UREG_I0
],
716 (int)regs
->u_regs
[UREG_I1
],
717 (int)regs
->u_regs
[UREG_I2
],
718 (int)regs
->u_regs
[UREG_I3
]);
722 asmlinkage
void solaris_register(void)
724 set_personality(PER_SVR4
);
727 extern long solaris_to_linux_signals
[], linux_to_solaris_signals
[];
729 struct exec_domain solaris_exec_domain
= {
732 .pers_low
= 1, /* PER_SVR4 personality */
734 .signal_map
= solaris_to_linux_signals
,
735 .signal_invmap
=linux_to_solaris_signals
,
736 .module
= THIS_MODULE
,
740 extern int init_socksys(void);
742 MODULE_AUTHOR("Jakub Jelinek (jj@ultra.linux.cz), Patrik Rak (prak3264@ss1000.ms.mff.cuni.cz)");
743 MODULE_DESCRIPTION("Solaris binary emulation module");
744 MODULE_LICENSE("GPL");
746 extern u32 tl0_solaris
[8];
747 #define update_ttable(x) \
748 tl0_solaris[3] = (((long)(x) - (long)tl0_solaris - 3) >> 2) | 0x40000000; \
750 __asm__ __volatile__ ("flush %0" : : "r" (&tl0_solaris[3]))
752 extern u32 solaris_sparc_syscall
[];
753 extern u32 solaris_syscall
[];
754 extern void cleanup_socksys(void);
756 extern u32 entry64_personality_patch
;
758 static int __init
solaris_init(void)
762 SOLDD(("Solaris module at %p\n", solaris_sparc_syscall
));
763 register_exec_domain(&solaris_exec_domain
);
764 if ((ret
= init_socksys())) {
765 unregister_exec_domain(&solaris_exec_domain
);
768 update_ttable(solaris_sparc_syscall
);
769 entry64_personality_patch
|=
770 (offsetof(struct task_struct
, personality
) +
771 (sizeof(unsigned long) - 1));
773 __asm__
__volatile__("flush %0"
774 : : "r" (&entry64_personality_patch
));
778 static void __exit
solaris_exit(void)
780 update_ttable(solaris_syscall
);
782 unregister_exec_domain(&solaris_exec_domain
);
785 module_init(solaris_init
);
786 module_exit(solaris_exit
);