1 /***************************************************************************
2  * \name ADM_folder_unix.cpp
3  * \author mean (c) 2006/2016
4  ***************************************************************************/
5 
6 /***************************************************************************
7  *                                                                         *
8  *   This program is free software; you can redistribute it and/or modify  *
9  *   it under the terms of the GNU General Public License as published by  *
10  *   the Free Software Foundation; either version 2 of the License, or     *
11  *   (at your option) any later version.                                   *
12  *                                                                         *
13  ***************************************************************************/
14 
15 #include <dirent.h>
16 #include <errno.h>
17 #include <sys/stat.h>
18 #include <string>
19 
20 #if defined(__APPLE__)
21 #	include <Carbon/Carbon.h>
22 #else
23 #	include <fcntl.h>
24 #endif
25 #include "ADM_default.h"
26 
27 #undef fopen
28 #undef mkdir
29 
30 /*
31 
32 ** note: it modifies it's first argument
33 */
simplify_path(char ** buf)34 void simplify_path(char **buf)
35 {
36 	unsigned int last1slash = 0;
37 	unsigned int last2slash = 0;
38 
39 	while (!strncmp(*buf, "/../", 4))
40 		memmove(*buf, *buf + 3, strlen(*buf + 3) + 1);
41 
42 	for (unsigned int i = 0; i < strlen(*buf) - 2; i++)
43 		while (!strncmp(*buf + i, "/./", 3))
44 			memmove(*buf + i, *buf + i + 2, strlen(*buf + i + 2) + 1);
45 
46 	for (unsigned int i = 0; i < strlen(*buf) - 3; i++)
47 	{
48 		if (*(*buf + i) == '/')
49 		{
50 			last2slash = last1slash;
51 			last1slash = i;
52 		}
53 
54 		if (!strncmp(*buf + i, "/../", 4))
55 		{
56 			memmove(*buf + last2slash, *buf + i + 3, strlen(*buf + i + 3) + 1);
57 
58 			return simplify_path(buf);
59 		}
60 	}
61 }
62 /**
63     \fn ADM_fopen
64     \brief utf8 aware fopen, so that we can use utf8 string even on win32
65 */
ADM_fopen(const char * file,const char * mode)66 FILE *ADM_fopen(const char *file, const char *mode)
67 {
68 	return fopen(file, mode);
69 }
70 
71 /**
72     \fn ADM_eraseFile
73 */
ADM_eraseFile(const char * file)74 uint8_t ADM_eraseFile(const char *file)
75 {
76     if(!unlink(file))
77         return true;
78     return false;
79 }
80 
81 /*----------------------------------------
82       Create a directory
83       If it already exists, do nothing
84 ------------------------------------------*/
ADM_mkdir(const char * dirname)85 uint8_t ADM_mkdir(const char *dirname)
86 {
87 	DIR *dir = NULL;
88 	uint8_t retVal = 0;
89 
90 	const char* dirname2 = dirname;
91 
92 	while (true)
93 	{
94 		// Check it already exists ?
95 		dir = opendir(dirname2);
96 
97 		if (dir)
98 		{
99 			printf("Directory %s exists.Good.\n", dirname);
100 			closedir(dir);
101 
102 			retVal = 1;
103 			break;
104 		}
105 		printf("Creating dir :%s\n", dirname2);
106 		mkdir(dirname2,0755);
107 
108 		if ((dir = opendir(dirname2)) == NULL)
109 			break;
110 
111 		closedir(dir);
112 
113 		retVal = 1;
114 
115 		break;
116 	}
117 
118 	return retVal;
119 }
120 /**
121  *  \fn buildDirectoryContent
122  * 	\brief Returns the content of a dir with the extension ext. The receiving array must be allocated by caller
123  * (just the array, not the names themselves)
124  */
buildDirectoryContent(uint32_t * outnb,const char * base,char * jobName[],int maxElems,const char * ext)125 uint8_t buildDirectoryContent(uint32_t *outnb, const char *base, char *jobName[], int maxElems, const char *ext)
126 {
127 	DIR *dir;
128 	struct dirent *direntry;
129 	int dirmax = 0, len;
130 	int extlen = strlen(ext)+1;
131     ADM_assert(extlen>1);
132 
133     char *dotted=(char *)admAlloca(extlen+1);
134     strcpy(dotted+1,ext);
135     dotted[0]='.';
136 
137 	const char *base2 = base;
138 
139 	dir = opendir(base2);
140 
141 
142 	if (!dir)
143 	{
144 		return 0;
145 	}
146 
147 
148 	while ((direntry = readdir(dir)))
149 	{
150 		const char *d_name = direntry->d_name;
151 
152 		len = strlen(d_name);
153 
154 		if (len < (extlen + 1))
155 			continue;
156 
157 		int xbase = len - extlen;
158 
159 		if (memcmp(d_name + xbase, dotted, extlen))
160 		{
161 			printf("ignored: %s\n", d_name);
162 			continue;
163 		}
164 
165 		jobName[dirmax] = (char *)ADM_alloc(strlen(base) + strlen(d_name) + 2);
166 		strcpy(jobName[dirmax], base);
167 		AddSeparator(jobName[dirmax]);
168 		strcat(jobName[dirmax], d_name);
169 		dirmax++;
170 
171 		if (dirmax >= maxElems)
172 		{
173 			printf("[jobs]: Max # of jobs exceeded\n");
174 			break;
175 		}
176 	}
177 
178 
179 	closedir(dir);
180 	*outnb = dirmax;
181 
182 	return 1;
183 }
184 
185 /**
186         \fn ADM_PathCanonize
187         \brief Canonize the path, returns a copy of the absolute path given as parameter
188 */
ADM_PathCanonize(const char * tmpname)189 char *ADM_PathCanonize(const char *tmpname)
190 {
191 	char path[300];
192 	char *out;
193 
194 	if (!getcwd(path, 300))
195 	{
196 		fprintf(stderr, "\ngetcwd() failed with: %s (%u)\n", strerror(errno), errno);
197 		path[0] = '\0';
198 	}
199 
200 	if (!tmpname || tmpname[0] == 0)
201 	{
202 		out = new char[strlen(path) + 2];
203 		strcpy(out, path);
204 		strcat(out, "/");
205 		printf("\n Canonizing null string ??? (%s)\n", out);
206 	}
207 	else if (tmpname[0] == '/'		)
208 	{
209 		out = new char[strlen(tmpname) + 1];
210 		strcpy(out, tmpname);
211 
212 		return out;
213 	}
214 	else
215 	{
216 		out = new char[strlen(path) + strlen(tmpname) + 6];
217 		strcpy(out, path);
218 		strcat(out, "/");
219 		strcat(out, tmpname);
220 	}
221 
222 	simplify_path(&out);
223 
224 	return out;
225 }
226 
227 /**
228         \fn ADM_extractPath
229 	\brief Returns path only /foo/bar.avi -> /foo
230 
231 */
ADM_extractPath(const std::string & str)232 std::string ADM_extractPath(const std::string &str)
233 {
234     std::string p;
235          p=str;
236          size_t idx=p.find_last_of ("/");
237          if(idx!=std::string::npos)
238             p.resize(idx);
239          return p;
240 }
241 /**
242 */
ADM_getFileName(const std::string & str)243 const std::string ADM_getFileName(const std::string &str)
244 {
245     size_t idx=str.find_last_of ("/");
246     if(idx==std::string::npos) return str;
247     return str.substr(idx+1);
248 }
249 
250 /**
251     \fn ADM_copyFile
252 */
ADM_renameFile(const char * source,const char * target)253 uint8_t ADM_renameFile(const char *source, const char *target)
254 {
255     if(!rename(source,target)) return true;
256     return false;
257 }
258 
259 
260 // EOF
261