t_setreuid.c revision 285830
163499Sps/*
263499Sps * Copyright (c) 2001 Proofpoint, Inc. and its suppliers.
363499Sps *	All rights reserved.
463499Sps *
563499Sps * By using this file, you agree to the terms and conditions set
663499Sps * forth in the LICENSE file which can be found at the top level of
763499Sps * the sendmail distribution.
863499Sps *
963499Sps */
1063499Sps
1163499Sps/*
1263499Sps**  This program checks to see if your version of setreuid works.
1363499Sps**  Compile it, make it set-user-ID root, and run it as yourself (NOT as
1463499Sps**  root).  If it won't compile or outputs any MAYDAY messages, don't
1563499Sps**  define HASSETREUID in conf.h.
1663499Sps**
1763499Sps**  Compilation is trivial -- just "cc t_setreuid.c".  Make it set-user-ID,
1863499Sps**  root and then execute it as a non-root user.
1963499Sps*/
2063499Sps
2163499Sps#include <sys/types.h>
2263499Sps#include <unistd.h>
2363499Sps#include <stdio.h>
2463499Sps
2563499Sps#ifndef lint
2663499Spsstatic char id[] = "@(#)$Id: t_setreuid.c,v 8.10 2013-11-22 20:52:01 ca Exp $";
2763812Sps#endif /* ! lint */
2863812Sps
2999112Sobrien#ifdef __hpux
3099112Sobrien# define setreuid(r, e)	setresuid(r, e, -1)
3163812Sps#endif /* __hpux */
3263499Sps
3363499Spsstatic void
3463499Spsprintuids(str, r, e)
3578717Sdd	char *str;
3663499Sps	uid_t r, e;
3763499Sps{
3863499Sps	printf("%s (should be %d/%d): r/euid=%d/%d\n", str, (int) r, (int) e,
39140811Sssouhlal	       (int) getuid(), (int) geteuid());
4063499Sps}
4163499Sps
4263499Spsint
4363499Spsmain(argc, argv)
4463499Sps	int argc;
4563499Sps	char **argv;
46140811Sssouhlal{
4763499Sps	int fail = 0;
48140865Sdelphij	uid_t realuid = getuid();
4963499Sps
50140865Sdelphij	printuids("initial uids", realuid, 0);
51140865Sdelphij
5263499Sps	if (geteuid() != 0)
53140865Sdelphij	{
5463499Sps		printf("SETUP ERROR: re-run set-user-ID root\n");
55140865Sdelphij		exit(1);
56140811Sssouhlal	}
57140865Sdelphij
58140865Sdelphij	if (getuid() == 0)
59140811Sssouhlal	{
60140811Sssouhlal		printf("SETUP ERROR: must be run by a non-root user\n");
6163499Sps		exit(1);
62140865Sdelphij	}
63140811Sssouhlal
64140865Sdelphij	if (setreuid(0, 1) < 0)
65140865Sdelphij	{
66140811Sssouhlal		fail++;
6763499Sps		printf("setreuid(0, 1) failure\n");
6863499Sps	}
69140865Sdelphij	printuids("after setreuid(0, 1)", 0, 1);
70140865Sdelphij
7163499Sps	if (getuid() != 0)
7263499Sps	{
73140811Sssouhlal		fail++;
74140865Sdelphij		printf("MAYDAY!  Wrong real uid\n");
7563499Sps	}
76140865Sdelphij
7763812Sps	if (geteuid() != 1)
7863499Sps	{
79140865Sdelphij		fail++;
8063499Sps		printf("MAYDAY!  Wrong effective uid\n");
81	}
82
83	/* do activity here */
84
85	if (setreuid(-1, 0) < 0)
86	{
87		fail++;
88		printf("setreuid(-1, 0) failure\n");
89	}
90	printuids("after setreuid(-1, 0)", 0, 0);
91	if (setreuid(realuid, 0) < 0)
92	{
93		fail++;
94		printf("setreuid(%d, 0) failure\n", (int) realuid);
95	}
96	printuids("after setreuid(realuid, 0)", realuid, 0);
97
98	if (geteuid() != 0)
99	{
100		fail++;
101		printf("MAYDAY!  Wrong effective uid\n");
102	}
103	if (getuid() != realuid)
104	{
105		fail++;
106		printf("MAYDAY!  Wrong real uid\n");
107	}
108	printf("\n");
109
110	if (setreuid(0, 2) < 0)
111	{
112		fail++;
113		printf("setreuid(0, 2) failure\n");
114	}
115	printuids("after setreuid(0, 2)", 0, 2);
116
117	if (geteuid() != 2)
118	{
119		fail++;
120		printf("MAYDAY!  Wrong effective uid\n");
121	}
122
123	if (getuid() != 0)
124	{
125		fail++;
126		printf("MAYDAY!  Wrong real uid\n");
127	}
128
129	/* do activity here */
130
131	if (setreuid(-1, 0) < 0)
132	{
133		fail++;
134		printf("setreuid(-1, 0) failure\n");
135	}
136	printuids("after setreuid(-1, 0)", 0, 0);
137	if (setreuid(realuid, 0) < 0)
138	{
139		fail++;
140		printf("setreuid(%d, 0) failure\n", (int) realuid);
141	}
142	printuids("after setreuid(realuid, 0)", realuid, 0);
143
144	if (geteuid() != 0)
145	{
146		fail++;
147		printf("MAYDAY!  Wrong effective uid\n");
148	}
149	if (getuid() != realuid)
150	{
151		fail++;
152		printf("MAYDAY!  Wrong real uid\n");
153	}
154
155	if (fail)
156	{
157		printf("\nThis system cannot use setreuid\n");
158		exit(1);
159	}
160
161	printf("\nIt is safe to define HASSETREUID on this system\n");
162	exit(0);
163}
164