xsindex.c
上传用户:lampled
上传日期:2007-01-07
资源大小:94k
文件大小:8k
源码类别:

Web服务器

开发平台:

Unix_Linux

  1. #include "config.h"
  2. #include <sys/types.h>
  3. #include <sys/stat.h>
  4. #include <unistd.h>
  5. #include <stdio.h>
  6. #include <stdlib.h>
  7. #include <fcntl.h>
  8. #ifdef HAVE_ERR_H
  9. #include <err.h>
  10. #else /* Not HAVE_ERR_H */
  11. #include "err.h"
  12. #endif /* HAVE_ERR_H */
  13. #include "string.h"
  14. #include "getopt.h"
  15. typedef struct mime
  16. {
  17. struct mime *n;
  18. char type[BUFSIZ], ext[BUFSIZ], icon[BUFSIZ],
  19. alt[BUFSIZ], small[BUFSIZ];
  20. } mime;
  21. static int show_size = 1, show_type = 1, show_back = 1,
  22. max_filename = 0, max_mimetype = 0, max_mimealt = 0,
  23. max_mimeshort = 0, force_overwrite = 0;
  24. static char mimefile[XS_PATH_MAX];
  25. static mime *mimes;
  26. #ifndef NOFORWARDS
  27. static VOID usage PROTO((void));
  28. static VOID loadmime PROTO((const char *));
  29. static const char *encode PROTO((const char *));
  30. static const char *neatsize PROTO((long));
  31. static const mime *findmime PROTO((const char *));
  32. #endif /* NOFORWARDS */
  33. static VOID
  34. usage DECL0
  35. {
  36. fprintf(stderr,
  37. "Usage: xsindex [-b] [-f] [-m mimefile] [-s] [-t number] titlen");
  38. fprintf(stderr, "   -b           Do not create a `back' link (..)n");
  39. fprintf(stderr, "   -f           Do not ask whether to overwrite %sn",
  40. INDEX_HTML);
  41. fprintf(stderr, "   -m mimefile  Use your own mime.index filen");
  42. fprintf(stderr, "                (default is %s/mime.index)n",
  43. HTTPD_ROOT);
  44. fprintf(stderr, "   -s           Do not give size of each filen");
  45. fprintf(stderr, "   -t number    Specify `file type' field options:n");
  46. fprintf(stderr, "                   1 - Full mime typen");
  47. fprintf(stderr, "                   2 - Short mime typen");
  48. fprintf(stderr, "                   3 - Do not give typesn");
  49. fprintf(stderr, "   title        Title of the %s pagen", INDEX_HTML);
  50. fprintf(stderr, "                Use "'s if it's more than one wordn");
  51. }
  52. static VOID
  53. loadmime DECL1C(char *, name)
  54. {
  55. FILE *input;
  56. char buffer[BUFSIZ], *end;
  57. mime *new;
  58. mimes = NULL;
  59. if (!(input = fopen(name, "r")))
  60. err(1, "fopen(`%s')", name);
  61. while (fgets(buffer, BUFSIZ, input))
  62. {
  63. if (strchr(buffer, '#'))
  64. *strchr(buffer, '#') = 0;
  65. end = buffer + strlen(buffer);
  66. while ((end > buffer) && (*(end - 1) <= ' '))
  67. *(--end) = 0;
  68. if (!buffer[0])
  69. continue;
  70. if (!(new = (mime *)malloc(sizeof(mime))))
  71. errx(1, "Out of memory in loadmime()");
  72. if (sscanf(buffer, "%s %s %s %s %[^n]n", new->type,
  73. new->ext, new->icon, new->alt, new->small) != 5)
  74. {
  75. fprintf(stderr, "Cannot parse line `%s'", buffer);
  76. continue;
  77. }
  78. new->n = mimes; mimes = new;
  79. }
  80. fclose(input);
  81. if (!mimes)
  82. errx(1, "Empty mime.index file: you need at least a default!");
  83. }
  84. static const char *
  85. encode DECL1C(char *, what)
  86. {
  87. static char buffer[BUFSIZ], *put;
  88. put = buffer;
  89. while (*what)
  90. {
  91. switch(*what)
  92. {
  93. case '<':
  94. strcpy(put, "&lt;"); put += 4;
  95. break;
  96. case '>':
  97. strcpy(put, "&gt;"); put += 4;
  98. break;
  99. case '&':
  100. strcpy(put, "&amp;"); put += 5;
  101. break;
  102. case '"':
  103. strcpy(put, "&quot;"); put += 6;
  104. break;
  105. default:
  106. *(put++) = *what;
  107. }
  108. what++;
  109. }
  110. *put = 0;
  111. return(buffer);
  112. }
  113. static const char *
  114. neatsize DECL1(long, size)
  115. {
  116. long temp;
  117. static char buffer1[BUFSIZ];
  118. char buffer2[BUFSIZ];
  119. buffer1[0] = 0;
  120. while (size)
  121. {
  122. temp = size / 1000;
  123. if (temp)
  124. sprintf(buffer2, "%03d,%s", (int)(size % 1000), buffer1);
  125. else
  126. sprintf(buffer2, "%d,%s", (int)(size % 1000), buffer1);
  127. strcpy(buffer1, buffer2);
  128. size = temp;
  129. }
  130. if (buffer1[0])
  131. buffer1[strlen(buffer1) - 1] = 0;
  132. else
  133. strcpy(buffer1, "0");
  134. return(buffer1);
  135. }
  136. static const mime *
  137. findmime DECL1C(char *, ext)
  138. {
  139. const mime *search;
  140. const char *end;
  141. if (!strcmp(ext, ".."))
  142. {
  143. end = "..";
  144. } else if (!strcmp(ext, ".directory."))
  145. {
  146. end = ".directory.";
  147. } else
  148. {
  149. end = strrchr(ext, '.');
  150. end = (end ? (end + 1) : "txt");
  151. }
  152. search = mimes;
  153. while (search)
  154. {
  155. if (!strcasecmp(search->ext, end))
  156. break;
  157. search = search->n;
  158. }
  159. if (!search)
  160. search = mimes;
  161. return(search);
  162. }
  163. extern int
  164. main DECL2(int, argc, char **, argv)
  165. {
  166. int option, amount, count;
  167. char **listing, buffer[BUFSIZ];
  168. FILE *output, *ls;
  169. struct stat statbuf;
  170. const mime *search;
  171. sprintf(mimefile, "%s/mime.index", HTTPD_ROOT);
  172. while ((option = getopt(argc, argv, "bfm:st:")) != EOF)
  173. {
  174. switch(option)
  175. {
  176. case 'b':
  177. show_back = 0;
  178. break;
  179. case 'f':
  180. force_overwrite = 1;
  181. break;
  182. case 'm':
  183. strcpy(mimefile, optarg);
  184. break;
  185. case 's':
  186. show_size = 0;
  187. break;
  188. case 't':
  189. show_type = atoi(optarg);
  190. if ((show_type < 1) || (show_type > 3))
  191. {
  192. usage();
  193. errx(1, "Invalid argument to -t");
  194. }
  195. break;
  196. default:
  197. usage();
  198. exit(1);
  199. }
  200. }
  201. if (optind != (argc - 1))
  202. {
  203. usage();
  204. exit(1);
  205. }
  206. loadmime(mimefile);
  207. if (!(ls = popen("ls -a", "r")))
  208. err(1, "popen(`ls -a', `r')");
  209. amount = 0;
  210. if (!(listing = (char **)malloc(16 * sizeof(char *))))
  211. errx(1, "Out of memory");
  212. while (fgets(buffer, BUFSIZ, ls))
  213. {
  214. if (buffer[0] && (buffer[strlen(buffer) - 1] < ' '))
  215. buffer[strlen(buffer) - 1] = 0;
  216. if (!strcmp(buffer, ".") || !strcmp(buffer, INDEX_HTML) ||
  217. !strcmp(buffer, ".xsuid") || !strcmp(buffer, ".noxs") ||
  218. !strcmp(buffer, ".xsauth"))
  219. continue;
  220. if ((strlen(buffer) >= 6) &&
  221. (!strcmp(buffer + strlen(buffer) - 6, ".redir")))
  222. continue;
  223. if (!strcmp(buffer, "..") && !show_back)
  224. continue;
  225. if (!(listing[amount] = (char *)malloc(strlen(buffer) + 1)))
  226. errx(1, "Out of memory");
  227. strcpy(listing[amount], buffer);
  228. if (max_filename < strlen(listing[amount]))
  229. max_filename = strlen(listing[amount]);
  230. if (!((amount + 1) & 0xf))
  231. {
  232. if (!(listing = (char **)realloc(listing,
  233. (amount + 17) * sizeof(char *))))
  234. errx(1, "Out of memory");
  235. }
  236. if (stat(listing[amount], &statbuf))
  237. err(1, "stat(`%s')", listing[amount]);
  238. if (statbuf.st_mode & S_IFDIR)
  239. search = findmime(".directory.");
  240. else
  241. search = findmime(listing[amount]);
  242. if (max_mimealt < strlen(search->alt))
  243. max_mimealt = strlen(search->alt);
  244. if (max_mimetype < strlen(search->type))
  245. max_mimetype = strlen(search->type);
  246. if (max_mimeshort < strlen(search->small))
  247. max_mimeshort = strlen(search->small);
  248. amount++;
  249. }
  250. pclose(ls);
  251. if (!force_overwrite && !access(INDEX_HTML, F_OK))
  252. {
  253. printf("A file called %s already exists.n", INDEX_HTML);
  254. printf("Do you want to overwrite it (y/n)? ");
  255. fflush(stdout);
  256. if (!fgets(buffer, BUFSIZ, stdin) || strcmp(buffer, "yn"))
  257. errx(1, "Cancelled on user's request");
  258. }
  259. remove(INDEX_HTML);
  260. if (!(output = fopen(INDEX_HTML, "w")))
  261. err(1, "fopen(%s)", INDEX_HTML);
  262. fprintf(output, "<HTML><HEAD><TITLE>%s</TITLE></HEAD><BODY>n",
  263. argv[optind]);
  264. fprintf(output, "<H1>%s</H1><HR><PRE>n", argv[optind]);
  265. for (count = 0; count < amount; count++)
  266. {
  267. if (stat(listing[count], &statbuf))
  268. err(1, "stat(`%s')", listing[count]);
  269. if (strcmp(listing[count], "..") && (statbuf.st_mode & S_IFDIR))
  270. search = findmime(".directory.");
  271. else
  272. search = findmime(listing[count]);
  273. fprintf(output, "<A HREF="%s">", encode(listing[count]));
  274. fprintf(output, "<IMG SRC="%s" ", encode(search->icon));
  275. fprintf(output, "ALT="[%s]%*.*s">", encode(search->alt),
  276. (int)(max_mimealt - strlen(search->alt)),
  277. (int)(max_mimealt - strlen(search->alt)), "");
  278. fprintf(output, "</A>  ");
  279. fprintf(output, "<A HREF="%s">", encode(listing[count]));
  280. fprintf(output, "%s</A>%*.*s    ", encode(listing[count]),
  281. (int)(max_filename - strlen(listing[count])),
  282. (int)(max_filename - strlen(listing[count])), "");
  283. switch(show_type)
  284. {
  285. case 1:
  286. fprintf(output, "%-*.*s", max_mimetype, max_mimetype,
  287. search->type);
  288. break;
  289. case 2:
  290. fprintf(output, "%-*.*s", max_mimeshort, max_mimeshort,
  291. search->small);
  292. break;
  293. default:
  294. break;
  295. }
  296. if (show_size && (statbuf.st_mode & S_IFREG))
  297. fprintf(output, "   %11.11s",
  298. neatsize((long)(statbuf.st_size)));
  299. fprintf(output, "n");
  300. }
  301. fclose(output);
  302. printf("`%s' is now ready...n", INDEX_HTML);
  303. exit(0);
  304. }