1// Copyright 2009-2021 Intel Corporation
2// SPDX-License-Identifier: Apache-2.0
3
4#include "filename.h"
5#include "sysinfo.h"
6
7namespace embree
8{
9#ifdef __WIN32__
10 const char path_sep = '\\';
11#else
12 const char path_sep = '/';
13#endif
14
15 /*! create an empty filename */
16 FileName::FileName () {}
17
18 /*! create a valid filename from a string */
19 FileName::FileName (const char* in) {
20 filename = in;
21 for (size_t i=0; i<filename.size(); i++)
22 if (filename[i] == '\\' || filename[i] == '/')
23 filename[i] = path_sep;
24 while (!filename.empty() && filename[filename.size()-1] == path_sep)
25 filename.resize(filename.size()-1);
26 }
27
28 /*! create a valid filename from a string */
29 FileName::FileName (const std::string& in) {
30 filename = in;
31 for (size_t i=0; i<filename.size(); i++)
32 if (filename[i] == '\\' || filename[i] == '/')
33 filename[i] = path_sep;
34 while (!filename.empty() && filename[filename.size()-1] == path_sep)
35 filename.resize(filename.size()-1);
36 }
37
38 /*! returns path to home folder */
39 FileName FileName::homeFolder()
40 {
41#ifdef __WIN32__
42 const char* home = getenv("UserProfile");
43#else
44 const char* home = getenv("HOME");
45#endif
46 if (home) return home;
47 return "";
48 }
49
50 /*! returns path to executable */
51 FileName FileName::executableFolder() {
52 return FileName(getExecutableFileName()).path();
53 }
54
55 /*! returns the path */
56 FileName FileName::path() const {
57 size_t pos = filename.find_last_of(path_sep);
58 if (pos == std::string::npos) return FileName();
59 return filename.substr(0,pos);
60 }
61
62 /*! returns the basename */
63 std::string FileName::base() const {
64 size_t pos = filename.find_last_of(path_sep);
65 if (pos == std::string::npos) return filename;
66 return filename.substr(pos+1);
67 }
68
69 /*! returns the extension */
70 std::string FileName::ext() const {
71 size_t pos = filename.find_last_of('.');
72 if (pos == std::string::npos) return "";
73 return filename.substr(pos+1);
74 }
75
76 /*! returns the extension */
77 FileName FileName::dropExt() const {
78 size_t pos = filename.find_last_of('.');
79 if (pos == std::string::npos) return filename;
80 return filename.substr(0,pos);
81 }
82
83 /*! returns the basename without extension */
84 std::string FileName::name() const {
85 size_t start = filename.find_last_of(path_sep);
86 if (start == std::string::npos) start = 0; else start++;
87 size_t end = filename.find_last_of('.');
88 if (end == std::string::npos || end < start) end = filename.size();
89 return filename.substr(start, end - start);
90 }
91
92 /*! replaces the extension */
93 FileName FileName::setExt(const std::string& ext) const {
94 size_t start = filename.find_last_of(path_sep);
95 if (start == std::string::npos) start = 0; else start++;
96 size_t end = filename.find_last_of('.');
97 if (end == std::string::npos || end < start) return FileName(filename+ext);
98 return FileName(filename.substr(0,end)+ext);
99 }
100
101 /*! adds the extension */
102 FileName FileName::addExt(const std::string& ext) const {
103 return FileName(filename+ext);
104 }
105
106 /*! concatenates two filenames to this/other */
107 FileName FileName::operator +( const FileName& other ) const {
108 if (filename == "") return FileName(other);
109 else return FileName(filename + path_sep + other.filename);
110 }
111
112 /*! concatenates two filenames to this/other */
113 FileName FileName::operator +( const std::string& other ) const {
114 return operator+(FileName(other));
115 }
116
117 /*! removes the base from a filename (if possible) */
118 FileName FileName::operator -( const FileName& base ) const {
119 size_t pos = filename.find_first_of(base);
120 if (pos == std::string::npos) return *this;
121 return FileName(filename.substr(pos+1));
122 }
123
124 /*! == operator */
125 bool operator== (const FileName& a, const FileName& b) {
126 return a.filename == b.filename;
127 }
128
129 /*! != operator */
130 bool operator!= (const FileName& a, const FileName& b) {
131 return a.filename != b.filename;
132 }
133
134 /*! output operator */
135 std::ostream& operator<<(std::ostream& cout, const FileName& filename) {
136 return cout << filename.filename;
137 }
138}
139