2 Unix SMB/Netbios implementation.
4 replacement routines for broken systems
5 Copyright (C) Andrew Tridgell 1992-1998
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
24 extern int DEBUGLEVEL;
26 void replace_dummy(void);
27 void replace_dummy(void) {}
30 #ifndef HAVE_FTRUNCATE
31 /*******************************************************************
32 ftruncate for operating systems that don't have it
33 ********************************************************************/
34 int ftruncate(int f,SMB_OFF_T l)
42 return fcntl(f, F_FREESP, &fl);
48 /*******************************************************************
49 a mktime() replacement for those who don't have it - contributed by
50 C.A. Lademann <cal@zls.com>
51 Corrections by richard.kettlewell@kewill.com
52 ********************************************************************/
55 #define HOUR 60*MINUTE
58 time_t mktime(struct tm *t)
63 int mon [] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 },
69 n = t->tm_year + 1900 - 1;
70 epoch = (t->tm_year - 70) * YEAR +
71 ((n / 4 - n / 100 + n / 400) - (1969 / 4 - 1969 / 100 + 1969 / 400)) * DAY;
76 for(i = 0; i < t->tm_mon; i++) {
77 epoch += mon [m] * DAY;
78 if(m == 1 && y % 4 == 0 && (y % 100 != 0 || y % 400 == 0))
87 epoch += (t->tm_mday - 1) * DAY;
88 epoch += t->tm_hour * HOUR + t->tm_min * MINUTE + t->tm_sec;
90 if((u = localtime(&epoch)) != NULL) {
91 t->tm_sec = u->tm_sec;
92 t->tm_min = u->tm_min;
93 t->tm_hour = u->tm_hour;
94 t->tm_mday = u->tm_mday;
95 t->tm_mon = u->tm_mon;
96 t->tm_year = u->tm_year;
97 t->tm_wday = u->tm_wday;
98 t->tm_yday = u->tm_yday;
99 t->tm_isdst = u->tm_isdst;
104 #endif /* !HAVE_MKTIME */
109 /* Rename a file. (from libiberty in GNU binutils) */
110 int rename(const char *zfrom, const char *zto)
112 if (link (zfrom, zto) < 0)
117 || link (zfrom, zto) < 0)
120 return unlink (zfrom);
127 * Search for a match in a netgroup. This replaces it on broken systems.
129 int innetgr(char *group,char *host,char *user,char *dom)
131 char *hst, *usr, *dm;
134 while (getnetgrent(&hst, &usr, &dm)) {
135 if (((host == 0) || (hst == 0) || !strcmp(host, hst)) &&
136 ((user == 0) || (usr == 0) || !strcmp(user, usr)) &&
137 ((dom == 0) || (dm == 0) || !strcmp(dom, dm))) {
149 #ifndef HAVE_INITGROUPS
150 /****************************************************************************
151 some systems don't have an initgroups call
152 ****************************************************************************/
153 int initgroups(char *name,gid_t id)
155 #ifndef HAVE_SETGROUPS
158 DEBUG(1,("WARNING: running without setgroups\n"));
161 /* yikes! no SETGROUPS or INITGROUPS? how can this work? */
164 gid_t grouplst[NGROUPS_MAX];
171 while (i < NGROUPS_MAX &&
172 ((g = (struct group *)getgrent()) != (struct group *)NULL)) {
177 while (gr && (*gr != (char)NULL)) {
178 if (strcmp(name,gr) == 0) {
179 grouplst[i] = g->gr_gid;
188 return(setgroups(i,grouplst));
194 #if (defined(SecureWare) && defined(SCO))
195 /* This is needed due to needing the nap() function but we don't want
196 to include the Xenix libraries since that will break other things...
197 BTW: system call # 0x0c28 is the same as calling nap() */
198 long nap(long milliseconds) {
199 return syscall(0x0c28, milliseconds);
205 /*******************************************************************
206 safely copies memory, ensuring no overlap problems.
207 this is only used if the machine does not have it's own memmove().
208 this is not the fastest algorithm in town, but it will do for our
210 ********************************************************************/
211 void *memmove(void *dest,const void *src,int size)
215 if (dest==src || !size) return(dest);
217 d = (unsigned long)dest;
218 s = (unsigned long)src;
220 if ((d >= (s+size)) || (s >= (d+size))) {
222 memcpy(dest,src,size);
227 /* we can forward copy */
228 if (s-d >= sizeof(int) &&
231 !(size%sizeof(int))) {
232 /* do it all as words */
233 int *idest = (int *)dest;
234 int *isrc = (int *)src;
236 for (i=0;i<size;i++) idest[i] = isrc[i];
239 char *cdest = (char *)dest;
240 char *csrc = (char *)src;
241 for (i=0;i<size;i++) cdest[i] = csrc[i];
244 /* must backward copy */
245 if (d-s >= sizeof(int) &&
248 !(size%sizeof(int))) {
249 /* do it all as words */
250 int *idest = (int *)dest;
251 int *isrc = (int *)src;
253 for (i=size-1;i>=0;i--) idest[i] = isrc[i];
256 char *cdest = (char *)dest;
257 char *csrc = (char *)src;
258 for (i=size-1;i>=0;i--) cdest[i] = csrc[i];
266 /****************************************************************************
268 ****************************************************************************/
269 char *strdup(const char *s)
274 if (!s) return(NULL);
277 ret = (char *)malloc(len);
278 if (!ret) return(NULL);
284 #ifdef REPLACE_INET_NTOA
285 char *rep_inet_ntoa(struct in_addr ip)
287 unsigned char *p = (unsigned char *)&ip.s_addr;
290 slprintf(buf, 17, "%d.%d.%d.%d",
291 (int)p[0], (int)p[1], (int)p[2], (int)p[3]);
293 slprintf(buf, 17, "%d.%d.%d.%d",
294 (int)p[3], (int)p[2], (int)p[1], (int)p[0]);