misc.c 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171
  1. /* Copyright (c) 1993-2007 by Richard Kelsey and Jonathan Rees.
  2. See file COPYING. */
  3. #include <stdio.h>
  4. #include <stdlib.h> /* for getenv(), etc. (POSIX?/ANSI) */
  5. #include <string.h> /* for strncpy(), etc. (POSIX/ANSI) */
  6. #include <pwd.h> /* for getpwnam() (POSIX.1) */
  7. #include <unistd.h> /* for sysconf(), etc. (POSIX.1/.2)*/
  8. #include <errno.h>
  9. #include <sys/stat.h>
  10. #include <locale.h> /* ISO C99 */
  11. #include <langinfo.h> /* SUSv2 */
  12. #include "sysdep.h"
  13. #include "c-mods.h"
  14. /*
  15. Expanding Unix filenames
  16. Unix Sucks
  17. Richard Kelsey Wed Jan 17 21:40:26 EST 1990
  18. Later modified by others who wish to remain anonymous
  19. Expands initial ~ and ~/ in string `name', leaving the result in `buffer'.
  20. `buffer_len' is the length of `buffer'.
  21. Note: strncpy(x, y, n) copies from y to x.
  22. */
  23. char *s48_expand_file_name (char *name, char *buffer, int buffer_len)
  24. {
  25. #define USER_NAME_SIZE 256
  26. char *dir, *p, user_name[USER_NAME_SIZE];
  27. struct passwd *user_data;
  28. int dir_len, i;
  29. int name_len = strlen(name);
  30. dir = 0;
  31. if (name[0] == '~') {
  32. name++; name_len--;
  33. if (name[0] == '/' || name[0] == 0) {
  34. dir = getenv("HOME"); }
  35. else {
  36. for (i = 0, p = name; i < name_len && *p != '/'; i++, p++)
  37. if (i > (USER_NAME_SIZE - 2)) {
  38. fprintf(stderr,
  39. "\ns48_expand_file_name: user name longer than %d characters\n",
  40. USER_NAME_SIZE - 3);
  41. return(NULL); };
  42. strncpy(user_name, name, i);
  43. user_name[i] = 0;
  44. user_data = getpwnam(user_name);
  45. if (!user_data) {
  46. fprintf(stderr, "\ns48_expand_file_name: unknown user \"%s\"\n",
  47. user_name);
  48. return(NULL); };
  49. name_len -= i;
  50. name = p;
  51. dir = user_data->pw_dir; } }
  52. else if (name[0] == '$') {
  53. name++; name_len--;
  54. for (i = 0, p = name; i < name_len && *p != '/'; i++, p++)
  55. if (i > (USER_NAME_SIZE - 2)) {
  56. fprintf(stderr,
  57. "\ns48_expand_file_name: environment variable longer than %d characters\n",
  58. USER_NAME_SIZE - 3);
  59. return(NULL); };
  60. strncpy(user_name, name, i);
  61. user_name[i] = 0;
  62. name_len -= i;
  63. name = p;
  64. dir = getenv(user_name); }
  65. if (dir) {
  66. dir_len = strlen(dir);
  67. if ((name_len + dir_len + 1) > buffer_len) {
  68. fprintf(stderr, "\ns48_expand_file_name: supplied buffer is too small\n");
  69. return(NULL); };
  70. strncpy(buffer, dir, dir_len);
  71. strncpy(buffer + dir_len, name, name_len);
  72. buffer[name_len + dir_len] = 0; }
  73. else {
  74. if ((name_len + 1) > buffer_len) {
  75. fprintf(stderr, "\ns48_expand_file_name: supplied buffer is too small\n");
  76. return(NULL); };
  77. strncpy(buffer, name, name_len);
  78. buffer[name_len] = 0; }
  79. return(buffer);
  80. }
  81. /* test routine
  82. main(argc, argv)
  83. int argc;
  84. char *argv[];
  85. {
  86. char buffer[32];
  87. s48_expand_file_name(argv[1], buffer, 32);
  88. printf("%s\n", buffer);
  89. return(0);
  90. }
  91. */
  92. /* Driver loop for tail-recursive calls */
  93. long s48_return_value;
  94. long
  95. s48_run_machine(long (*proc) (void))
  96. {
  97. while (proc != 0)
  98. proc = (long (*) (void)) (*proc)();
  99. return s48_return_value;
  100. }
  101. unsigned char *
  102. ps_error_string(long the_errno)
  103. {
  104. return((unsigned char *)strerror(the_errno));
  105. }
  106. /* Getting the length of a file. */
  107. long
  108. s48_get_file_size(unsigned char *name)
  109. {
  110. struct stat file_data;
  111. int status;
  112. if (-1 == stat((char*)name, &file_data) ||
  113. ! S_ISREG(file_data.st_mode))
  114. return -1;
  115. else
  116. return file_data.st_size;
  117. }
  118. /* encoding of argv */
  119. char*
  120. s48_get_os_string_encoding(void)
  121. {
  122. static char setlocale_called = PSFALSE;
  123. char *codeset;
  124. static char* encoding = NULL;
  125. /* Mike has no clue what the rationale for needing this is. */
  126. if (!setlocale_called)
  127. {
  128. setlocale(LC_CTYPE, "");
  129. setlocale_called = PSTRUE;
  130. }
  131. if (encoding == NULL)
  132. {
  133. codeset = nl_langinfo(CODESET); /* this ain't reentrant */
  134. encoding = malloc(strlen(codeset) + 1);
  135. if (encoding == NULL)
  136. return NULL;
  137. strcpy(encoding, codeset);
  138. }
  139. return encoding;
  140. }