aboutsummaryrefslogtreecommitdiff
path: root/secmem/util.c
blob: 580fd344d40c9f3d18113393eb9b786de6cfaf6f (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
/* Quintuple Agent
 * Copyright (C) 1999 Robert Bihlmeyer <robbe@orcus.priv.at>
 *
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation; either version 2 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program; if not, write to the Free Software
 *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 */

#define _GNU_SOURCE 1

#include <unistd.h>
#include <errno.h>
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>

#ifdef HAVE_CONFIG_H
#include "config.h"
#endif

#include "util.h"

#ifndef TEMP_FAILURE_RETRY
#define TEMP_FAILURE_RETRY(expression) \
  (__extension__							      \
    ({ long int __result;						      \
       do __result = (long int) (expression);				      \
       while (__result == -1L && errno == EINTR);			      \
       __result; }))
#endif

#ifndef HAVE_DOSISH_SYSTEM
static int uid_set = 0;
static uid_t real_uid, file_uid;
#endif /*!HAVE_DOSISH_SYSTEM*/

/* write DATA of size BYTES to FD, until all is written or an error occurs */
ssize_t xwrite(int fd, const void *data, size_t bytes)
{
  char *ptr;
  size_t todo;
  ssize_t written = 0;

  for (ptr = (char *)data, todo = bytes; todo; ptr += written, todo -= written)
    if ((written = TEMP_FAILURE_RETRY(write(fd, ptr, todo))) < 0)
      break;
  return written;
}

#if 0
extern int debug;

int debugmsg(const char *fmt, ...)
{
  va_list va;
  int ret;

  if (debug) {
    va_start(va, fmt);
    fprintf(stderr, "\e[4m");
    ret = vfprintf(stderr, fmt, va);
    fprintf(stderr, "\e[24m");
    va_end(va);
    return ret;
  } else
    return 0;
}
#endif

/* initialize uid variables */
#ifndef HAVE_DOSISH_SYSTEM
static void init_uids(void)
{
  real_uid = getuid();
  file_uid = geteuid();
  uid_set = 1;
}
#endif


#if 0 /* Not used. */
/* lower privileges to the real user's */
void lower_privs()
{
  if (!uid_set)
    init_uids();
  if (real_uid != file_uid) {
#ifdef HAVE_SETEUID
    if (seteuid(real_uid) < 0) {
      perror("lowering privileges failed");
      exit(EXIT_FAILURE);
    }
#else
    fprintf(stderr, _("Warning: running q-agent setuid on this system is dangerous\n"));
#endif /* HAVE_SETEUID */
  }
}
#endif /* if 0 */

#if 0 /* Not used. */
/* raise privileges to the effective user's */
void raise_privs()
{
  assert(real_uid >= 0);	/* lower_privs() must be called before this */
#ifdef HAVE_SETEUID
  if (real_uid != file_uid && seteuid(file_uid) < 0) {
   perror("Warning: raising privileges failed");
  }
#endif /* HAVE_SETEUID */
}
#endif /* if 0 */

/* drop all additional privileges */
void drop_privs()
{
#ifndef HAVE_DOSISH_SYSTEM
  if (!uid_set)
    init_uids();
  if (real_uid != file_uid) {
    if (setuid(real_uid) < 0) {
      perror("dropping privileges failed");
      exit(EXIT_FAILURE);
    }
    file_uid = real_uid;
  }
#endif
}