getpwent_a.c 1.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354
  1. #include "pwf.h"
  2. #include <pthread.h>
  3. static unsigned atou(char **s)
  4. {
  5. unsigned x;
  6. for (x=0; **s-'0'<10U; ++*s) x=10*x+(**s-'0');
  7. return x;
  8. }
  9. int __getpwent_a(FILE *f, struct passwd *pw, char **line, size_t *size, struct passwd **res)
  10. {
  11. ssize_t l;
  12. char *s;
  13. int rv = 0;
  14. int cs;
  15. pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cs);
  16. for (;;) {
  17. if ((l=getline(line, size, f)) < 0) {
  18. rv = ferror(f) ? errno : 0;
  19. free(*line);
  20. *line = 0;
  21. pw = 0;
  22. break;
  23. }
  24. line[0][l-1] = 0;
  25. s = line[0];
  26. pw->pw_name = s++;
  27. if (!(s = strchr(s, ':'))) continue;
  28. *s++ = 0; pw->pw_passwd = s;
  29. if (!(s = strchr(s, ':'))) continue;
  30. *s++ = 0; pw->pw_uid = atou(&s);
  31. if (*s != ':') continue;
  32. *s++ = 0; pw->pw_gid = atou(&s);
  33. if (*s != ':') continue;
  34. *s++ = 0; pw->pw_gecos = s;
  35. if (!(s = strchr(s, ':'))) continue;
  36. *s++ = 0; pw->pw_dir = s;
  37. if (!(s = strchr(s, ':'))) continue;
  38. *s++ = 0; pw->pw_shell = s;
  39. break;
  40. }
  41. pthread_setcancelstate(cs, 0);
  42. *res = pw;
  43. if (rv) errno = rv;
  44. return rv;
  45. }