#include #include #include // #include "socket.h" struct group* getgrnam(const char *name); /* for AS225 */ #define PATH_GROUP "inet:db/group" #define MAXGRP 200 #define MAXLINELENGTH 1024 #define UNIX_STRSEP ":\n" #define AMIGAOS_STRSEP "|\n" static gid_t nextgid; /* ** builtin group info */ static char *dummy_members[] = { 0 }; static const struct group builtin_wheel = { "wheel", "*", 0, dummy_members }; static const struct group builtin_nogroup = { "nogroup", "*", -2, dummy_members }; /* ** */ static int gr_start(struct SocketSettings *lss) { if (lss->lx_grp_fp) { rewind(lss->lx_grp_fp); return 1; } return ((lss->lx_grp_fp = fopen(PATH_GROUP, "r")) != 0 ? 1 : 0); } static int gr_scan(int search, gid_t gid, const char *name, struct SocketSettings *lss) { if (!lss->lx_grp_line) lss->lx_grp_line = malloc(MAXLINELENGTH + 1); if (!lss->lx_members) lss->lx_members = malloc(MAXGRP * sizeof(char*)); if (!lss->lx_grp_line || !lss->lx_members) { errno = ENOMEM; return 0; } for (;;) { char *sep, *bp, *cp, **m; if (!fgets(lss->lx_grp_line, MAXLINELENGTH, lss->lx_grp_fp)) return 0; /* skip lines that are too big */ if (!strchr(lss->lx_grp_line, '\n')) { int ch; while ((ch = getc(lss->lx_grp_fp)) != '\n' && ch != EOF) ; continue; } sep = strchr(bp = lss->lx_grp_line, '|') ? AMIGAOS_STRSEP : UNIX_STRSEP; lss->lx_grp.gr_name = strsep(&bp, sep); if (search && name && strcmp(lss->lx_grp.gr_name, name)) continue; lss->lx_grp.gr_passwd = strsep(&bp, sep); if (!(cp = strsep(&bp, sep))) continue; lss->lx_grp.gr_gid = atoi(cp); if (search && !name && lss->lx_grp.gr_gid != gid) continue; for (lss->lx_grp.gr_mem = (m = lss->lx_members);; ++m) { if (m == &lss->lx_members[MAXGRP - 1]) { *m = NULL; break; } if ((*m = strsep(&bp, ", \n")) == NULL) break; } break; } return 1; } /* ** */ int setgroupent(int stayopen) { struct SocketSettings *lss = _lx_get_socket_settings(); if (lss->lx_network_type == LX_AMITCP) { UG_setgrent(); } else { nextgid = 0; if (gr_start(lss)) lss->lx_grp_stayopen = stayopen; } return 1; } void setgrent(void) { setgroupent(0); } void endgrent(void) { struct SocketSettings *lss = _lx_get_socket_settings(); if (lss->lx_network_type == LX_AMITCP) { UG_endgrent(); } else { nextgid = 0; if (lss->lx_grp_fp) { fclose(lss->lx_grp_fp); lss->lx_grp_fp = NULL; } } } struct group* getgrent(void) { struct SocketSettings *lss = _lx_get_socket_settings(); if (lss->lx_network_type == LX_AMITCP) { return UG_getgrent(); } else if ((lss->lx_grp_fp || gr_start(lss)) && gr_scan(0, 0, NULL, lss)) { return &lss->lx_grp; } else if (lss->lx_network_type == LX_NONE) { char *name; switch (nextgid) { case 0: nextgid = 1; return (struct group*) &builtin_wheel; default: nextgid = -2; if ((name = getenv("GROUP"))) return getgrnam(name); /* no break */ case (gid_t) (-2): nextgid = -1; return (struct group*) &builtin_nogroup; case (gid_t) (-1): //return NULL; break; } } return NULL; } struct group* getgrgid(gid_t gid) { struct SocketSettings *lss; if (gid == (gid_t) (-2)) return (struct group*) &builtin_nogroup; /* always handle nogroup */ lss = _lx_get_socket_settings(); if (lss->lx_network_type == LX_AMITCP) { struct group *grp = UG_getgrgid(gid); if (!grp) errno = ug_GetErr(); return grp; } else if (gr_start(lss)) { int rval = gr_scan(1, gid, NULL, lss); if (!lss->lx_grp_stayopen) endgrent(); return (rval ? &lss->lx_grp : NULL); } else if (lss->lx_network_type == LX_NONE) { if (gid == 0) return (struct group*) &builtin_wheel; if ((gid == getgid()) && (lss->lx_grp.gr_name = getenv("GROUP"))) { lss->lx_grp.gr_gid = gid; lss->lx_grp.gr_passwd = "*"; lss->lx_grp.gr_mem = dummy_members; return &lss->lx_grp; } } return NULL; } struct group* getgrnam(const char *name) { struct SocketSettings *lss; if (!strcmp(name, "nogroup")) return (struct group*) &builtin_nogroup; /* always handle nogroup */ lss = _lx_get_socket_settings(); if (lss->lx_network_type == LX_AMITCP) { struct group *grp = UG_getgrnam(name); if (!grp) errno = ug_GetErr(); return grp; } else if (gr_start(lss)) { int rval = gr_scan(1, 0, name, lss); if (!lss->lx_grp_stayopen) endgrent(); return (rval ? &lss->lx_grp : NULL); } else if (lss->lx_network_type == LX_NONE) { if (!strcmp(name, "wheel")) return (struct group*) &builtin_wheel; if ((lss->lx_grp.gr_name = getenv("GROUP")) && !strcmp(lss->lx_grp.gr_name, name)) { lss->lx_grp.gr_gid = getgid(); lss->lx_grp.gr_passwd = "*"; lss->lx_grp.gr_mem = dummy_members; return &lss->lx_grp; } } return NULL; }