1: <?php
2: 3: 4: 5: 6: 7: 8: 9: 10:
11:
12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23:
24:
25: class XoopsPathController
26: {
27: 28: 29:
30: public $xoopsPath = array(
31: 'root' => '', 'lib' => '', 'data' => '',
32: );
33:
34: 35: 36:
37: public $xoopsPathDefault = array(
38: 'lib' => 'xoops_lib', 'data' => 'xoops_data',
39: );
40:
41: 42: 43:
44: public $dataPath = array(
45: 'caches' => array(
46: 'xoops_cache', 'smarty_cache', 'smarty_compile',
47: ), 'configs',
48: );
49:
50: 51: 52:
53: public $path_lookup = array(
54: 'root' => 'ROOT_PATH', 'data' => 'VAR_PATH', 'lib' => 'PATH',
55: );
56:
57: 58: 59:
60: public $xoopsUrl = '';
61:
62: 63: 64:
65: public $validPath = array(
66: 'root' => 0, 'data' => 0, 'lib' => 0,
67: );
68:
69: 70: 71:
72: public $validUrl = false;
73:
74: 75: 76:
77: public $permErrors = array(
78: 'root' => null, 'data' => null,
79: );
80:
81: 82: 83: 84:
85: public function __construct($xoopsPathDefault, $dataPath)
86: {
87: $this->xoopsPathDefault = $xoopsPathDefault;
88: $this->dataPath = $dataPath;
89:
90: if (isset($_SESSION['settings']['ROOT_PATH'])) {
91: foreach ($this->path_lookup as $req => $sess) {
92: $this->xoopsPath[$req] = $_SESSION['settings'][$sess];
93: }
94: } else {
95: $path = str_replace("\\", "/", realpath('../'));
96: if (substr($path, -1) === '/') {
97: $path = substr($path, 0, -1);
98: }
99: if (file_exists("$path/mainfile.dist.php")) {
100: $this->xoopsPath['root'] = $path;
101: }
102:
103: $this->xoopsPath['lib'] = dirname($path) . "/" . ($this->xoopsPathDefault['lib']);
104:
105: if (!is_dir($this->xoopsPath['lib'] . "/")) {
106: $this->xoopsPath['lib'] = $path . "/" . ($this->xoopsPathDefault['lib']);
107: }
108:
109: $this->xoopsPath['data'] = dirname($path) . "/" . ($this->xoopsPathDefault['data']);
110:
111: if (!is_dir($this->xoopsPath['data'] . "/")) {
112: $this->xoopsPath['data'] = $path . "/" . ($this->xoopsPathDefault['data']);
113: }
114: }
115: if (isset($_SESSION['settings']['URL'])) {
116: $this->xoopsUrl = $_SESSION['settings']['URL'];
117: } else {
118:
119: $wizard = $_SESSION['wizard'];
120: $path = $wizard->baseLocation();
121: $this->xoopsUrl = substr($path, 0, strrpos($path, '/'));
122: }
123: }
124:
125: 126: 127:
128: public function execute()
129: {
130:
131: $wizard = $_SESSION['wizard'];
132:
133: $this->readRequest();
134: $valid = $this->validate();
135: if ($_SERVER['REQUEST_METHOD'] === 'POST') {
136: foreach ($this->path_lookup as $req => $sess) {
137: $_SESSION['settings'][$sess] = $this->xoopsPath[$req];
138: }
139: $_SESSION['settings']['URL'] = $this->xoopsUrl;
140: if ($valid) {
141: $wizard->redirectToPage('+1');
142: } else {
143: $wizard->redirectToPage('+0');
144: }
145: }
146: }
147:
148: 149: 150:
151: public function readRequest()
152: {
153: if ($_SERVER['REQUEST_METHOD'] === 'POST') {
154: $request = $_POST;
155: foreach ($this->path_lookup as $req => $sess) {
156: if (isset($request[$req])) {
157: $request[$req] = str_replace("\\", "/", trim($request[$req]));
158: if (substr($request[$req], -1) === '/') {
159: $request[$req] = substr($request[$req], 0, -1);
160: }
161: $this->xoopsPath[$req] = $request[$req];
162: }
163: }
164: if (isset($request['URL'])) {
165: $request['URL'] = trim($request['URL']);
166: if (substr($request['URL'], -1) === '/') {
167: $request['URL'] = substr($request['URL'], 0, -1);
168: }
169: $this->xoopsUrl = $request['URL'];
170: }
171: }
172: }
173:
174: public function validate()
175: {
176: foreach (array_keys($this->xoopsPath) as $path) {
177: if ($this->checkPath($path)) {
178: $this->checkPermissions($path);
179: }
180: }
181: $this->validUrl = !empty($this->xoopsUrl);
182: $validPaths = (array_sum(array_values($this->validPath)) == count(array_keys($this->validPath))) ? 1 : 0;
183: $validPerms = true;
184: foreach ($this->permErrors as $errs) {
185: if (empty($errs)) {
186: continue;
187: }
188: foreach ($errs as $status) {
189: if (empty($status)) {
190: $validPerms = false;
191: break;
192: }
193: }
194: }
195: return ($validPaths && $this->validUrl && $validPerms);
196: }
197:
198: public function checkPath($PATH = '')
199: {
200: $ret = 1;
201: if ($PATH === 'root' || empty($PATH)) {
202: $path = 'root';
203: if (is_dir($this->xoopsPath[$path]) && is_readable($this->xoopsPath[$path])) {
204: @include_once "{$this->xoopsPath[$path]}/include/version.php";
205: if (file_exists("{$this->xoopsPath[$path]}/mainfile.dist.php") && defined('XOOPS_VERSION')) {
206: $this->validPath[$path] = 1;
207: }
208: }
209: $ret *= $this->validPath[$path];
210: }
211: if ($PATH === 'lib' || empty($PATH)) {
212: $path = 'lib';
213: if (is_dir($this->xoopsPath[$path]) && is_readable($this->xoopsPath[$path])) {
214: $this->validPath[$path] = 1;
215: }
216: $ret *= $this->validPath[$path];
217: }
218: if ($PATH === 'data' || empty($PATH)) {
219: $path = 'data';
220: if (is_dir($this->xoopsPath[$path]) && is_readable($this->xoopsPath[$path])) {
221: $this->validPath[$path] = 1;
222: }
223: $ret *= $this->validPath[$path];
224: }
225: return $ret;
226: }
227:
228: public function setPermission($parent, $path, &$error)
229: {
230: if (is_array($path)) {
231: foreach (array_keys($path) as $item) {
232: if (is_string($item)) {
233: $error[$parent . "/" . $item] = $this->makeWritable($parent . "/" . $item);
234: if (empty($path[$item])) {
235: continue;
236: }
237: foreach ($path[$item] as $child) {
238: $this->setPermission($parent . "/" . $item, $child, $error);
239: }
240: } else {
241: $error[$parent . "/" . $path[$item]] = $this->makeWritable($parent . "/" . $path[$item]);
242: }
243: }
244: } else {
245: $error[$parent . "/" . $path] = $this->makeWritable($parent . "/" . $path);
246: }
247: return;
248: }
249:
250: 251: 252: 253:
254: public function checkPermissions($path)
255: {
256: $paths = array(
257: 'root' => array('mainfile.php', 'uploads', ), 'data' => $this->dataPath
258: );
259: $errors = array(
260: 'root' => null, 'data' => null,
261: );
262:
263: if (!isset($this->xoopsPath[$path])) {
264: return false;
265: }
266: if (!isset($errors[$path])) {
267: return true;
268: }
269: $this->setPermission($this->xoopsPath[$path], $paths[$path], $errors[$path]);
270: if (in_array(false, $errors[$path])) {
271: $this->permErrors[$path] = $errors[$path];
272: }
273: return true;
274: }
275:
276: 277: 278: 279: 280: 281: 282:
283: public function makeWritable($path, $create = true)
284: {
285: $mode = intval('0777', 8);
286: if (!file_exists($path)) {
287: if (!$create) {
288: return false;
289: } else {
290: mkdir($path, $mode);
291: }
292: }
293: if (!is_writable($path)) {
294: chmod($path, $mode);
295: }
296: clearstatcache();
297: if (is_writable($path)) {
298: $info = stat($path);
299: if ($info['mode'] & 0002) {
300: return 'w';
301: } elseif ($info['mode'] & 0020) {
302: return 'g';
303: }
304: return 'u';
305: }
306: return false;
307: }
308: }
309: