home *** CD-ROM | disk | FTP | other *** search
-
-
- /*
- * chup.c - change uid of a running process.
- * Should work on any 4.2/4.3BSD based kernel.
- * Written by Avalon (avalon@coombs.anu.edu.au), 22/12/93.
-
- Ported to SunOS by x0d, me thinks.
- */
-
- #include <stdio.h>
- #include <sys/types.h>
- #include <unistd.h>
- #include <sys/param.h>
- #define KERNEL
- #include <sys/file.h>
- #undef KERNEL
- #include <nlist.h>
- #include <sys/types.h>
- #include <sys/user.h>
- #include <sys/proc.h>
- #include <sys/ucred.h>
- /* #include <sys/processflags.h> /**/
-
- #ifndef offsetof
- #define offsetof(t,m) (int)((&((t *)0L)->m))
- #endif
-
- #define DEVKMEM "/home/new-kmem"
-
- struct nlist names[] = {
- { "_allproc", 0, 0, 0, 0},
- { (char *)NULL, 0, 0, 0, 0 }
- };
-
- static int kfd = -1, pid = -1, uid = -1, euid = -1, debug = 0;
-
- void fatal(status, msg)
- int status;
- char *msg;
- {
- perror(msg);
- exit(status);
- }
-
- static int lock_on() {
- return 0;
- }
-
- static int lock_off() {
- return 0;
- }
-
- int kopen() {
- return (kfd = open(DEVKMEM, O_RDWR));
- }
-
- void kread(buf, pos, n)
- char *buf;
- off_t pos;
- int n;
- {
- if (!n) return;
- if (debug) printf("read %d @%#x to %#x on %d\n", n, pos, buf, kfd);
- if (lseek(kfd, pos, 0) == -1) fatal(-1, "k(r)lseek");
- if (read(kfd, buf, n) != n) fatal(-1, "kread");
- }
-
- int kwrite(buf, pos, size)
- char *buf;
- u_long pos, size;
- {
- if (lseek(kfd, pos, 0) == -1) fatal(-1, "k(w)lseek");
- if (debug) printf("write %d to %#x from %#x on %d\n", size, pos, buf, kfd);
- if (write(kfd, buf, size) == -1) fatal(-1, "kwrite");
- return 0;
- }
-
- int change_proc() {
- register int i;
- int np;
- struct proc p,*next;
- struct ucred ucr;
-
- if (nlist("/vmunix", names) == -1) fatal(-1, "nlist");
- if (kopen() == -1) fatal(-1, DEVKMEM);
- if (lock_on() == -1) return -1;
- if(names[0].n_value ==0) fatal(-1, "no allproc");
- kill(pid, SIGSTOP);
- kread((char *)&next, names[0].n_value, sizeof(struct proc *));
- /* walk the linked list */
- for (i = 0; next; i++) {
- kread((char *)&p, (char *)next, sizeof(p));
- next = p.p_nxt;
- if (p.p_pid == pid) {
- if(!p.p_cred) fatal(-1, "no credentials with this process!");
- kread((char *)&ucr, (char *)p.p_cred, sizeof(ucr));
- printf("%d %d (uid %d, suid %d) uid %d euid %d\n",
- i, p.p_pid, p.p_uid, p.p_suid, ucr.cr_ruid,ucr.cr_uid);
- if (uid != -1) {
- ucr.cr_ruid = uid;
- kwrite((char *)&ucr + offsetof(struct ucred, cr_ruid),
- (char *)p.p_cred + offsetof(struct ucred, cr_ruid),
- sizeof(ucr.cr_ruid));
- }
- if(euid != -1) {
- ucr.cr_uid = euid;
- kwrite((char *)&ucr + offsetof(struct ucred, cr_uid),
- (char *)p.p_cred + offsetof(struct ucred, cr_uid),
- sizeof(ucr.cr_uid));
- }
- printf("set to %d %d\n", uid, euid);
- break;
- }
- }
- kill(pid, SIGCONT);
- if (!next) (void) fprintf(stderr, "process %d not found\n", pid);
- /* we're not going through that again :)
- else {
- kread((char *)p, (char *)pt + i * sizeof(*p), sizeof(*p));
- kread((char *)&pcr, (char *)p->p_cred, sizeof(pcr));
- if(pcr.pc_ucred != NOCRED) kread((char *)&ucr, (char *)pcr.pc_ucred, si
- zeof(ucr));
- (void) printf("%d %d uid %d euid %d\n", i, p->p_pid, pcr.p_ruid,
- (pcr.pc_ucred!=NOCRED)? ucr.cr_uid : pcr.p_ruid);
- }
- */
- lock_off();
- }
-
- void printusage(name)
- char *name;
- {
- (void) fprintf(stderr, "usage:\n%s <pid> [uid [euid]]\n", name);
- }
-
- int do_args(argc, argv)
- int argc;
- char *argv[];
- {
- if (argv[1] && !strcmp(argv[1], "-d")) argv++, argc--, debug = 1;
- if (argc == 1) {
- printusage(argv[0]);
- return -1;
- }
- if (kill(pid = atoi(argv[1]), 0) == -1) {
- perror(argv[0]);
- return -1;
- }
- if (argc > 2) {
- uid = atoi(argv[2]);
- if (argc > 3) euid = atoi(argv[3]);
- }
- return 0;
- }
-
- main(argc, argv)
- int argc;
- char *argv[];
- {
- if (do_args(argc, argv)) exit(1);
- return change_proc();
- }
-
-
-
-