]> git.donarmstrong.com Git - lilypond.git/blob - flower/file-path.cc
* Documentation/pictures/lilypond-48.xpm: New file.
[lilypond.git] / flower / file-path.cc
1 /*
2   file-path.cc - implement File_path
3
4   source file of the Flower Library
5
6   (c) 1997--2005 Han-Wen Nienhuys <hanwen@cs.uu.nl>
7   Jan Nieuwenhuizen <janneke@gnu.org>
8 */
9
10 #include "file-path.hh"
11
12 #include <cstdio>
13 #include <cerrno>
14
15 #include "config.hh"
16 #if HAVE_SYS_STAT_H
17 #include <sys/stat.h>
18 #endif
19
20 #ifdef __CYGWIN__
21 #include <sys/cygwin.h>
22 #endif
23
24 #include "file-name.hh"
25
26 #ifndef PATHSEP
27 #define PATHSEP ':'
28 #endif
29
30 Array<String>
31 File_path::directories () const
32 {
33   return *this;
34 }
35
36 void
37 File_path::parse_path (String p)
38 {
39   int len;
40   while ((len = p.length ()) )
41     {
42       int i = p.index (PATHSEP);
43       if (i <0) 
44         i = len;
45       append (p.left_string (i));
46       p = p.right_string (len - i - 1);
47     }
48 }
49
50 /** Find a file.
51
52 Check absolute file name, search in the current dir (DUH! FIXME!),
53 in the construction-arg (what's that?), and in any other appended
54 directory, in this order.
55
56 @return
57 The file name if found, or empty string if not found. */
58
59 String
60 File_path::find (String name) const
61 {
62   if (!name.length () || (name == "-"))
63     return name;
64
65   /* Handle absolute file name.  */
66   if (name[0] == DIRSEP)
67     {
68       if (FILE *f = fopen (name.to_str0 (), "r"))
69         {
70           fclose (f);
71           return name;
72         }
73     }
74
75   for (int i = 0; i < size (); i++)
76     {
77       String file_name = elem (i);
78       String sep = ::to_string (DIRSEP);
79       String right (file_name.right_string (1));
80       if (file_name.length () && right != sep)
81         file_name += ::to_string (DIRSEP);
82
83       file_name += name;
84
85 #if 0 /* Check if directory. TODO: encapsulate for autoconf */
86       struct stat sbuf;
87       if (stat (file_name.to_str0 (), &sbuf) != 0)
88         continue;
89
90       if (! (sbuf.st_mode & __S_IFREG))
91         continue;
92 #endif
93 #if !STAT_MACROS_BROKEN
94
95       struct stat sbuf;
96       if (stat (file_name.to_str0 (), &sbuf) != 0)
97         continue;
98
99       if (S_ISDIR (sbuf.st_mode))
100         continue;
101 #endif
102
103       /* ugh */
104       FILE *f = fopen (file_name.to_str0 (), "r");
105       if (f)
106         {
107           fclose (f);
108           return file_name;
109         }
110     }
111   return "";
112 }
113
114 /** Find a file.
115
116 Seach in the current dir (DUH! FIXME?), in the construction-arg
117 (what's that?, and in any other appended directory, in this order.
118
119 Search for NAME, or name without extension, or name with any of
120 EXTENSIONS, in that order.
121
122 @return
123 The file name if found, or empty string if not found. */
124 String
125 File_path::find (String name, char const *extensions[])
126 {
127   File_name file_name (name);
128   if (name.is_empty () || name == "-")
129     file_name.base_ = "-";
130   else
131     {
132       String orig_ext = file_name.ext_;
133       for (int i = 0; extensions[i]; i++)
134         {
135           file_name.ext_ = orig_ext;
136           if (*extensions[i] && !file_name.ext_.is_empty ())
137             file_name.ext_ += ".";
138           file_name.ext_ += extensions[i];
139           if (!find (file_name.to_string ()).is_empty ())
140             break;
141         }
142       /* Reshuffle extension */
143       file_name = File_name (file_name.to_string ());
144     }
145   return file_name.to_string ();
146 }
147
148 /** Append a directory, return false if failed.  */
149 bool
150 File_path::try_append (String s)
151 {
152   if (s == "")
153     s = ".";
154   if (FILE *f = fopen (s.to_str0 (), "r"))
155     {
156       fclose (f);
157       append (s);
158       return true;
159     }
160   return false;
161 }
162
163 String
164 File_path::to_string () const
165 {
166   String s;
167   int n = size ();
168   for (int i = 0; i < n; i++)
169     {
170       s = s + elem (i);
171       if (i < n - 1)
172         s += ::to_string (PATHSEP);
173     }
174   return s;
175 }