Rev 1278 | Rev 1430 | Go to most recent revision | Show entire file | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 1278 | Rev 1426 | ||
---|---|---|---|
Line 61... | Line 61... | ||
61 | 61 | ||
62 | if (!OIDplus::authUtils()->isAdminLoggedIn()) { |
62 | if (!OIDplus::authUtils()->isAdminLoggedIn()) { |
63 | throw new OIDplusHtmlException(_L('You need to <a %1>log in</a> as administrator.',OIDplus::gui()->link('oidplus:login$admin')), $out['title'], 401); |
63 | throw new OIDplusHtmlException(_L('You need to <a %1>log in</a> as administrator.',OIDplus::gui()->link('oidplus:login$admin')), $out['title'], 401); |
64 | } |
64 | } |
65 | 65 | ||
66 | $out['text'] = '<p>'._L('This tool compares the checksums of the files of your OIDplus installation with the checksums of the OIDplus original SVN version.').'<br>'; |
66 | $out['text'] = '<p>'._L('This tool compares the checksums of the files of your OIDplus installation with the checksums of the OIDplus original version.').'<br>'; |
67 | $out['text'] .= _L('Differences could have various reasons, for example, a hotfix you have applied.').'<br>'; |
67 | $out['text'] .= _L('Differences could have various reasons, for example, a hotfix you have applied.').'<br>'; |
68 | $out['text'] .= _L('The folders "userdata" and "userdata_pub" as well as third-party-plugins (folder "plugins" excluding "viathinksoft") are not listed.').'</p>'; |
68 | $out['text'] .= _L('The folders "userdata" and "userdata_pub" as well as third-party-plugins (folder "plugins" excluding "viathinksoft") are not listed.').'</p>'; |
69 | $out['text'] .= '<p>'._L('Please note: If you believe that you were hacked, you should not trust the output of this tool, because it might be compromised, too.').'</p>'; |
69 | $out['text'] .= '<p>'._L('Please note: If you believe that you were hacked, you should not trust the output of this tool, because it might be compromised, too.').'</p>'; |
70 | 70 | ||
71 | if ($parts[1] !== 'go') { |
71 | if ($parts[1] !== 'go') { |
72 | $out['text'] .= '<p><input type="button" '.OIDplus::gui()->link('oidplus:system_file_check$go').' value="'._L('Start scan').'"> ('._L('Attention: Takes a long time!').')</p>'; |
72 | $out['text'] .= '<p><input type="button" '.OIDplus::gui()->link('oidplus:system_file_check$go').' value="'._L('Start scan').'"></p>'; |
73 | } else { |
73 | } else { |
74 | @set_time_limit(0); |
74 | @set_time_limit(0); |
75 | 75 | ||
76 | $ver = OIDplus::getVersion(); |
- | |
77 | if (substr($ver,0,4) !== 'svn-') { |
- | |
78 | $out['text'] = '<p><font color="red">'.mb_strtoupper(_L('Error')).': '._L('Cannot determine version of the system').'</font></p>'; |
- | |
79 | return; |
- | |
80 | } |
- | |
81 | $ver = substr($ver,strlen('svn-')); |
- | |
82 | - | ||
83 | - | ||
84 | $out['text'] .= '<h2>'._L('Result (comparison with SVN revision %1)', $ver).'</h2>'; |
76 | $out['text'] .= '<h2>'._L('Result').'</h2>'; |
85 | 77 | ||
86 | $out['text'] .= '<pre>'; |
78 | $out['text'] .= '<pre>'; |
87 | 79 | ||
88 | try { |
80 | try { |
89 | $theirs = self::checksumFileToArray(sprintf(OIDplus::getEditionInfo()['checksum_file'],$ver)); |
81 | $theirs = json_decode(file_get_contents(__DIR__.'/checksums.json'),true); |
90 | if ($theirs === false) { |
- | |
91 | throw new OIDplusException(_L("Cannot download checksum file. Please try again later.")); |
- | |
92 | } |
- | |
93 | 82 | ||
- | 83 | $exclude = [ |
|
- | 84 | // Please keep in-sync with private/gen_serverside_v3 |
|
- | 85 | realpath(__DIR__.'/checksums.json'), |
|
- | 86 | realpath(OIDplus::localpath().'/userdata'), |
|
- | 87 | realpath(OIDplus::localpath().'/userdata_pub') |
|
- | 88 | ]; |
|
94 | $mine = self::getDirContents(OIDplus::localpath()); |
89 | $mine = self::getDirContents(OIDplus::localpath(), null, $exclude); |
95 | 90 | ||
96 | $num = 0; |
91 | $num = 0; |
97 | 92 | ||
98 | foreach ($mine as $filename_old => $hash_old) { |
93 | foreach ($mine as $filename_old => $hash_old) { |
99 | $filename_old = str_replace('\\', '/', $filename_old); |
94 | $filename_old = str_replace('\\', '/', $filename_old); |
Line 101... | Line 96... | ||
101 | if ( |
96 | if ( |
102 | (substr($filename_old, 0, strlen('userdata/')) !== 'userdata/') && |
97 | (substr($filename_old, 0, strlen('userdata/')) !== 'userdata/') && |
103 | (substr($filename_old, 0, strlen('userdata_pub/')) !== 'userdata_pub/') && |
98 | (substr($filename_old, 0, strlen('userdata_pub/')) !== 'userdata_pub/') && |
104 | 99 | ||
105 | // Don't list third-party plugins |
100 | // Don't list third-party plugins |
- | 101 | // TODO: but bundled ones should be listed! |
|
106 | (( |
102 | # (( |
107 | (substr($filename_old, 0, strlen('plugins/')) === 'plugins/') && |
103 | # (substr($filename_old, 0, strlen('plugins/')) === 'plugins/') && |
108 | ( |
104 | # ( |
109 | (explode('/',$filename_old)[1] === 'viathinksoft') || |
105 | # (explode('/',$filename_old)[1] === 'viathinksoft') || |
110 | (explode('/',$filename_old)[1] === 'index.html') || |
106 | # (explode('/',$filename_old)[1] === 'index.html') || |
111 | (substr(explode('/',$filename_old)[1],-4) === '.xsd') |
107 | # (substr(explode('/',$filename_old)[1],-4) === '.xsd') |
112 | ) |
108 | # ) |
113 | ) || (substr($filename_old, 0, strlen('plugins/')) !== 'plugins/')) && |
109 | # ) || (substr($filename_old, 0, strlen('plugins/')) !== 'plugins/')) && |
114 | 110 | ||
115 | ($filename_old !== 'oidplus_version.txt') && |
- | |
116 | ($filename_old !== '.version.php') && |
111 | ($filename_old !== 'composer.lock') && |
117 | ($filename_old !== 'composer.lock') |
112 | ($filename_old !== 'plugins/viathinksoft/adminPages/902_systemfile_check/checksums.json') |
118 | ){ |
113 | ){ |
119 | $num++; |
114 | $num++; |
120 | if (is_dir(OIDplus::localpath().$filename_old)) { |
115 | if (is_dir(OIDplus::localpath().$filename_old)) { |
121 | $out['text'] .= "<b>"._L('Additional directory').":</b> $filename_old\n"; |
116 | $out['text'] .= "<b>"._L('Additional directory').":</b> $filename_old\n"; |
122 | } else { |
117 | } else { |
Line 136... | Line 131... | ||
136 | foreach ($mine as $filename_old => $hash_old) { |
131 | foreach ($mine as $filename_old => $hash_old) { |
137 | if (isset($theirs[$filename_old])) { |
132 | if (isset($theirs[$filename_old])) { |
138 | $hash_new = $theirs[$filename_old]; |
133 | $hash_new = $theirs[$filename_old]; |
139 | if ($hash_old != $hash_new) { |
134 | if ($hash_old != $hash_new) { |
140 | $num++; |
135 | $num++; |
141 | $svn_url = sprintf(OIDplus::getEditionInfo()['svn_original'],urlencode($filename_old),urlencode($ver)); |
- | |
142 | $out['text'] .= "<b>"._L('Checksum mismatch').":</b> $filename_old (<a target=\"_blank\" href=\"$svn_url\">"._L('Expected file contents')."</a>)\n"; |
136 | $out['text'] .= "<b>"._L('Checksum mismatch').":</b> $filename_old\n"; |
143 | } |
137 | } |
144 | } |
138 | } |
145 | } |
139 | } |
146 | 140 | ||
147 | if ($num == 0) { |
141 | if ($num == 0) { |
Line 194... | Line 188... | ||
194 | } |
188 | } |
195 | 189 | ||
196 | /** |
190 | /** |
197 | * @param string $dir |
191 | * @param string $dir |
198 | * @param string|null $basepath |
192 | * @param string|null $basepath |
- | 193 | * @param array $exclude |
|
199 | * @param array $results |
194 | * @param array $results |
200 | * @return array |
195 | * @return array |
201 | */ |
196 | */ |
202 | private static function getDirContents(string $dir, string $basepath = null, array &$results = array()): array { |
197 | public static function getDirContents(string $dir, string $basepath = null, array $exclude=[], array &$results=[]): array { |
203 | if (is_null($basepath)) $basepath = $dir; |
198 | if (is_null($basepath)) $basepath = $dir; |
204 | $basepath = realpath($basepath) . DIRECTORY_SEPARATOR; |
199 | $basepath = realpath($basepath) . DIRECTORY_SEPARATOR; |
205 | $dir = realpath($dir) . DIRECTORY_SEPARATOR; |
200 | $dir = realpath($dir) . DIRECTORY_SEPARATOR; |
206 | $files = scandir($dir); |
201 | $files = scandir($dir); |
207 | foreach ($files as $file) { |
202 | foreach ($files as $file) { |
208 | $path = realpath($dir . DIRECTORY_SEPARATOR . $file); |
203 | $path = realpath($dir . DIRECTORY_SEPARATOR . $file); |
- | 204 | if (in_array($path,$exclude)) continue; |
|
209 | if (empty($path)) $path = $dir . DIRECTORY_SEPARATOR . $file; |
205 | if (empty($path)) $path = $dir . DIRECTORY_SEPARATOR . $file; |
- | 206 | if ($file == 'composer.lock') continue; |
|
210 | if (!is_dir($path)) { |
207 | if (!is_dir($path)) { |
211 | $xpath = substr($path, strlen($basepath)); |
208 | $xpath = substr($path, strlen($basepath)); |
212 | $xpath = str_replace('\\', '/', $xpath); |
209 | $xpath = str_replace('\\', '/', $xpath); |
213 | $results[$xpath] = @hash_file('sha256', $path); |
210 | $results[$xpath] = @hash_file('sha256', $path); |
214 | } else if ($file != "." && $file != ".." && $file != ".svn" && $file != ".git") { |
211 | } else if ($file != "." && $file != ".." && $file != ".svn" && $file != ".git") { |
215 | self::getDirContents($path, $basepath, $results); |
212 | self::getDirContents($path, $basepath, $exclude, $results); |
216 | $xpath = substr($path, strlen($basepath)); |
213 | $xpath = substr($path, strlen($basepath)); |
217 | $xpath = str_replace('\\', '/', $xpath); |
214 | $xpath = str_replace('\\', '/', $xpath); |
218 | $results[$xpath] = hash('sha256', ''); |
215 | $results[$xpath] = hash('sha256', ''); |
219 | } |
216 | } |
220 | } |
217 | } |
221 | return $results; |
218 | return $results; |
222 | } |
219 | } |
223 | 220 | ||
224 | /** |
- | |
225 | * @param string $checksumfile |
- | |
226 | * @return array|false |
- | |
227 | */ |
- | |
228 | private static function checksumFileToArray(string $checksumfile) { |
- | |
229 | $out = array(); |
- | |
230 | - | ||
231 | $cont = url_get_contents($checksumfile); |
- | |
232 | if ($cont === false) return false; |
- | |
233 | $lines = explode("\n", $cont); |
- | |
234 | - | ||
235 | foreach ($lines as $line) { |
- | |
236 | $line = trim($line); |
- | |
237 | if ($line == '') continue; |
- | |
238 | list($hash, $filename) = explode("\t",$line); |
- | |
239 | if (substr($filename,0,strlen('trunk/')) == 'trunk/') { |
- | |
240 | $out[substr($filename,strlen('trunk/'))] = $hash; |
- | |
241 | } |
- | |
242 | } |
- | |
243 | return $out; |
- | |
244 | } |
- | |
245 | - | ||
246 | } |
221 | } |