aboutsummaryrefslogtreecommitdiff
path: root/contrib/texinfo/info/dir.c
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/texinfo/info/dir.c')
-rw-r--r--contrib/texinfo/info/dir.c273
1 files changed, 0 insertions, 273 deletions
diff --git a/contrib/texinfo/info/dir.c b/contrib/texinfo/info/dir.c
deleted file mode 100644
index 4ccf85613101..000000000000
--- a/contrib/texinfo/info/dir.c
+++ /dev/null
@@ -1,273 +0,0 @@
-/* dir.c -- How to build a special "dir" node from "localdir" files. */
-
-/* This file is part of GNU Info, a program for reading online documentation
- stored in Info format.
-
- Copyright (C) 1993 Free Software Foundation, Inc.
-
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 2, or (at your option)
- any later version.
-
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this program; if not, write to the Free Software
- Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
-
- Written by Brian Fox (bfox@ai.mit.edu). */
-
-#include <stdio.h>
-#include <sys/types.h>
-#include <sys/stat.h>
-#if defined (HAVE_SYS_FILE_H)
-#include <sys/file.h>
-#endif /* HAVE_SYS_FILE_H */
-#include <sys/errno.h>
-#include "info-utils.h"
-#include "filesys.h"
-#include "tilde.h"
-
-/* The "dir" node can be built from the contents of a file called "dir",
- with the addition of the menus of every file named in the array
- dirs_to_add which are found in INFOPATH. */
-
-static void add_menu_to_file_buffer (), insert_text_into_fb_at_binding ();
-static void build_dir_node_internal ();
-
-static char *dirs_to_add[] = {
- "dir", "localdir", (char *)NULL
-};
-
-void
-maybe_build_dir_node (dirname)
- char *dirname;
-{
- FILE_BUFFER *dir_buffer;
- int path_index, update_tags;
- char *this_dir;
-
- /* Check to see if the file has already been built. If so, then
- do not build it again. */
- dir_buffer = info_find_file (dirname);
-
- /* If there is no "dir" in the current info path, we cannot build one
- from nothing. */
- if (!dir_buffer)
- return;
-
- /* If this directory has already been built, return now. */
- if (dir_buffer->flags & N_CannotGC)
- return;
-
- path_index = update_tags = 0;
-
- /* Using each element of the path, check for one of the files in
- DIRS_TO_ADD. Do not check for "localdir.info.Z" or anything else.
- Only files explictly named are eligible. This is a design decision.
- There can be an info file name "localdir.info" which contains
- information on the setting up of "localdir" files. */
- while (this_dir = extract_colon_unit (infopath, &path_index))
- {
- register int da_index;
- char *from_file;
-
- /* Expand a leading tilde if one is present. */
- if (*this_dir == '~')
- {
- char *tilde_expanded_dirname;
-
- tilde_expanded_dirname = tilde_expand_word (this_dir);
- if (tilde_expanded_dirname != this_dir)
- {
- free (this_dir);
- this_dir = tilde_expanded_dirname;
- }
- }
-
- /* For every file named in DIRS_TO_ADD found in the search path,
- add the contents of that file's menu to our "dir" node. */
- for (da_index = 0; from_file = dirs_to_add[da_index]; da_index++)
- {
- struct stat finfo;
- char *fullpath;
- int namelen, statable;
-
- namelen = strlen (from_file);
-
- fullpath = (char *)xmalloc (3 + strlen (this_dir) + namelen);
- strcpy (fullpath, this_dir);
- if (fullpath[strlen (fullpath) - 1] != '/')
- strcat (fullpath, "/");
- strcat (fullpath, from_file);
-
- statable = (stat (fullpath, &finfo) == 0);
-
- /* Only add the contents of this file if it is not identical to the
- file of the DIR buffer. */
- if ((statable && S_ISREG (finfo.st_mode)) &&
- (strcmp (dir_buffer->fullpath, fullpath) != 0))
- {
- long filesize;
- char *contents;
-
- contents = filesys_read_info_file (fullpath, &filesize, &finfo);
-
- if (contents)
- {
- update_tags++;
- add_menu_to_file_buffer (contents, filesize, dir_buffer);
- free (contents);
- }
- }
-
- free (fullpath);
- }
- free (this_dir);
- }
-
- if (update_tags)
- build_tags_and_nodes (dir_buffer);
-
- /* Flag that the dir buffer has been built. */
- dir_buffer->flags |= N_CannotGC;
-}
-
-/* Given CONTENTS and FB (a file buffer), add the menu found in CONTENTS
- to the menu found in FB->contents. Second argument SIZE is the total
- size of CONTENTS. */
-static void
-add_menu_to_file_buffer (contents, size, fb)
- char *contents;
- long size;
- FILE_BUFFER *fb;
-{
- SEARCH_BINDING contents_binding, fb_binding;
- long contents_offset, fb_offset;
-
- contents_binding.buffer = contents;
- contents_binding.start = 0;
- contents_binding.end = size;
- contents_binding.flags = S_FoldCase | S_SkipDest;
-
- fb_binding.buffer = fb->contents;
- fb_binding.start = 0;
- fb_binding.end = fb->filesize;
- fb_binding.flags = S_FoldCase | S_SkipDest;
-
- /* Move to the start of the menus in CONTENTS and FB. */
- contents_offset = search_forward (INFO_MENU_LABEL, &contents_binding);
- fb_offset = search_forward (INFO_MENU_LABEL, &fb_binding);
-
- /* If there is no menu in CONTENTS, quit now. */
- if (contents_offset == -1)
- return;
-
- /* There is a menu in CONTENTS, and contents_offset points to the first
- character following the menu starter string. Skip all whitespace
- and newline characters. */
- contents_offset += skip_whitespace_and_newlines (contents + contents_offset);
-
- /* If there is no menu in FB, make one. */
- if (fb_offset == -1)
- {
- /* Find the start of the second node in this file buffer. If there
- is only one node, we will be adding the contents to the end of
- this node. */
- fb_offset = find_node_separator (&fb_binding);
-
- /* If not even a single node separator, give up. */
- if (fb_offset == -1)
- return;
-
- fb_binding.start = fb_offset;
- fb_binding.start +=
- skip_node_separator (fb_binding.buffer + fb_binding.start);
-
- /* Try to find the next node separator. */
- fb_offset = find_node_separator (&fb_binding);
-
- /* If found one, consider that the start of the menu. Otherwise, the
- start of this menu is the end of the file buffer (i.e., fb->size). */
- if (fb_offset != -1)
- fb_binding.start = fb_offset;
- else
- fb_binding.start = fb_binding.end;
-
- insert_text_into_fb_at_binding
- (fb, &fb_binding, INFO_MENU_LABEL, strlen (INFO_MENU_LABEL));
-
- fb_binding.buffer = fb->contents;
- fb_binding.start = 0;
- fb_binding.end = fb->filesize;
- fb_offset = search_forward (INFO_MENU_LABEL, &fb_binding);
- if (fb_offset == -1)
- abort ();
- }
-
- /* CONTENTS_OFFSET and FB_OFFSET point to the starts of the menus that
- appear in their respective buffers. Add the remainder of CONTENTS
- to the end of FB's menu. */
- fb_binding.start = fb_offset;
- fb_offset = find_node_separator (&fb_binding);
- if (fb_offset != -1)
- fb_binding.start = fb_offset;
- else
- fb_binding.start = fb_binding.end;
-
- /* Leave exactly one blank line between directory entries. */
- {
- int num_found = 0;
-
- while ((fb_binding.start > 0) &&
- (whitespace_or_newline (fb_binding.buffer[fb_binding.start - 1])))
- {
- num_found++;
- fb_binding.start--;
- }
-
- /* Optimize if possible. */
- if (num_found >= 2)
- {
- fb_binding.buffer[fb_binding.start++] = '\n';
- fb_binding.buffer[fb_binding.start++] = '\n';
- }
- else
- {
- /* Do it the hard way. */
- insert_text_into_fb_at_binding (fb, &fb_binding, "\n\n", 2);
- fb_binding.start += 2;
- }
- }
-
- /* Insert the new menu. */
- insert_text_into_fb_at_binding
- (fb, &fb_binding, contents + contents_offset, size - contents_offset);
-}
-
-static void
-insert_text_into_fb_at_binding (fb, binding, text, textlen)
- FILE_BUFFER *fb;
- SEARCH_BINDING *binding;
- char *text;
- int textlen;
-{
- char *contents;
- long start, end;
-
- start = binding->start;
- end = fb->filesize;
-
- contents = (char *)xmalloc (fb->filesize + textlen + 1);
- memcpy (contents, fb->contents, start);
- memcpy (contents + start, text, textlen);
- memcpy (contents + start + textlen, fb->contents + start, end - start);
- free (fb->contents);
- fb->contents = contents;
- fb->filesize += textlen;
- fb->finfo.st_size = fb->filesize;
-}