]> git.mxchange.org Git - quix0rs-gnu-social.git/blob - plugins/CasAuthentication/extlib/CAS.php
Merge branch '0.9.x' into 1.0.x
[quix0rs-gnu-social.git] / plugins / CasAuthentication / extlib / CAS.php
1 <?php\r
2 \r
3 /*\r
4  * Copyright © 2003-2010, The ESUP-Portail consortium & the JA-SIG Collaborative.\r
5  * All rights reserved.\r
6  * \r
7  * Redistribution and use in source and binary forms, with or without\r
8  * modification, are permitted provided that the following conditions are met:\r
9  * \r
10  *     * Redistributions of source code must retain the above copyright notice,\r
11  *       this list of conditions and the following disclaimer.\r
12  *     * Redistributions in binary form must reproduce the above copyright notice,\r
13  *       this list of conditions and the following disclaimer in the documentation\r
14  *       and/or other materials provided with the distribution.\r
15  *     * Neither the name of the ESUP-Portail consortium & the JA-SIG\r
16  *       Collaborative nor the names of its contributors may be used to endorse or\r
17  *       promote products derived from this software without specific prior\r
18  *       written permission.\r
19 \r
20  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND\r
21  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\r
22  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\r
23  * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR\r
24  * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\r
25  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\r
26  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON\r
27  * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\r
28  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\r
29  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\r
30  */\r
31 \r
32 //\r
33 // hack by Vangelis Haniotakis to handle the absence of $_SERVER['REQUEST_URI'] in IIS\r
34 //\r
35 if (!$_SERVER['REQUEST_URI']) {\r
36         $_SERVER['REQUEST_URI'] = $_SERVER['SCRIPT_NAME'] . '?' . $_SERVER['QUERY_STRING'];\r
37 }\r
38 \r
39 //\r
40 // another one by Vangelis Haniotakis also to make phpCAS work with PHP5\r
41 //\r
42 if (version_compare(PHP_VERSION, '5', '>=') && !(function_exists('domxml_new_doc'))) {\r
43         require_once (dirname(__FILE__) . '/CAS/domxml-php4-to-php5.php');\r
44 }\r
45 \r
46 /**\r
47  * @file CAS/CAS.php\r
48  * Interface class of the phpCAS library\r
49  *\r
50  * @ingroup public\r
51  */\r
52 \r
53 // ########################################################################\r
54 //  CONSTANTS\r
55 // ########################################################################\r
56 \r
57 // ------------------------------------------------------------------------\r
58 //  CAS VERSIONS\r
59 // ------------------------------------------------------------------------\r
60 \r
61 /**\r
62  * phpCAS version. accessible for the user by phpCAS::getVersion().\r
63  */\r
64 define('PHPCAS_VERSION', '1.1.2');\r
65 \r
66 // ------------------------------------------------------------------------\r
67 //  CAS VERSIONS\r
68 // ------------------------------------------------------------------------\r
69 /**\r
70  * @addtogroup public\r
71  * @{\r
72  */\r
73 \r
74 /**\r
75  * CAS version 1.0\r
76  */\r
77 define("CAS_VERSION_1_0", '1.0');\r
78 /*!\r
79  * CAS version 2.0\r
80  */\r
81 define("CAS_VERSION_2_0", '2.0');\r
82 \r
83 // ------------------------------------------------------------------------\r
84 //  SAML defines\r
85 // ------------------------------------------------------------------------\r
86 \r
87 /**\r
88  * SAML protocol\r
89  */\r
90 define("SAML_VERSION_1_1", 'S1');\r
91 \r
92 /**\r
93  * XML header for SAML POST\r
94  */\r
95 define("SAML_XML_HEADER", '<?xml version="1.0" encoding="UTF-8"?>');\r
96 \r
97 /**\r
98  * SOAP envelope for SAML POST\r
99  */\r
100 define("SAML_SOAP_ENV", '<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"><SOAP-ENV:Header/>');\r
101 \r
102 /**\r
103  * SOAP body for SAML POST\r
104  */\r
105 define("SAML_SOAP_BODY", '<SOAP-ENV:Body>');\r
106 \r
107 /**\r
108  * SAMLP request\r
109  */\r
110 define("SAMLP_REQUEST", '<samlp:Request xmlns:samlp="urn:oasis:names:tc:SAML:1.0:protocol"  MajorVersion="1" MinorVersion="1" RequestID="_192.168.16.51.1024506224022" IssueInstant="2002-06-19T17:03:44.022Z">');\r
111 define("SAMLP_REQUEST_CLOSE", '</samlp:Request>');\r
112 \r
113 /**\r
114  * SAMLP artifact tag (for the ticket)\r
115  */\r
116 define("SAML_ASSERTION_ARTIFACT", '<samlp:AssertionArtifact>');\r
117 \r
118 /**\r
119  * SAMLP close\r
120  */\r
121 define("SAML_ASSERTION_ARTIFACT_CLOSE", '</samlp:AssertionArtifact>');\r
122 \r
123 /**\r
124  * SOAP body close\r
125  */\r
126 define("SAML_SOAP_BODY_CLOSE", '</SOAP-ENV:Body>');\r
127 \r
128 /**\r
129  * SOAP envelope close\r
130  */\r
131 define("SAML_SOAP_ENV_CLOSE", '</SOAP-ENV:Envelope>');\r
132 \r
133 /**\r
134  * SAML Attributes\r
135  */\r
136 define("SAML_ATTRIBUTES", 'SAMLATTRIBS');\r
137 \r
138 /** @} */\r
139 /**\r
140  * @addtogroup publicPGTStorage\r
141  * @{\r
142  */\r
143 // ------------------------------------------------------------------------\r
144 //  FILE PGT STORAGE\r
145 // ------------------------------------------------------------------------\r
146 /**\r
147  * Default path used when storing PGT's to file\r
148  */\r
149 define("CAS_PGT_STORAGE_FILE_DEFAULT_PATH", '/tmp');\r
150 /**\r
151  * phpCAS::setPGTStorageFile()'s 2nd parameter to write plain text files\r
152  */\r
153 define("CAS_PGT_STORAGE_FILE_FORMAT_PLAIN", 'plain');\r
154 /**\r
155  * phpCAS::setPGTStorageFile()'s 2nd parameter to write xml files\r
156  */\r
157 define("CAS_PGT_STORAGE_FILE_FORMAT_XML", 'xml');\r
158 /**\r
159  * Default format used when storing PGT's to file\r
160  */\r
161 define("CAS_PGT_STORAGE_FILE_DEFAULT_FORMAT", CAS_PGT_STORAGE_FILE_FORMAT_PLAIN);\r
162 // ------------------------------------------------------------------------\r
163 //  DATABASE PGT STORAGE\r
164 // ------------------------------------------------------------------------\r
165 /**\r
166  * default database type when storing PGT's to database\r
167  */\r
168 define("CAS_PGT_STORAGE_DB_DEFAULT_DATABASE_TYPE", 'mysql');\r
169 /**\r
170  * default host when storing PGT's to database\r
171  */\r
172 define("CAS_PGT_STORAGE_DB_DEFAULT_HOSTNAME", 'localhost');\r
173 /**\r
174  * default port when storing PGT's to database\r
175  */\r
176 define("CAS_PGT_STORAGE_DB_DEFAULT_PORT", '');\r
177 /**\r
178  * default database when storing PGT's to database\r
179  */\r
180 define("CAS_PGT_STORAGE_DB_DEFAULT_DATABASE", 'phpCAS');\r
181 /**\r
182  * default table when storing PGT's to database\r
183  */\r
184 define("CAS_PGT_STORAGE_DB_DEFAULT_TABLE", 'pgt');\r
185 \r
186 /** @} */\r
187 // ------------------------------------------------------------------------\r
188 // SERVICE ACCESS ERRORS\r
189 // ------------------------------------------------------------------------\r
190 /**\r
191  * @addtogroup publicServices\r
192  * @{\r
193  */\r
194 \r
195 /**\r
196  * phpCAS::service() error code on success\r
197  */\r
198 define("PHPCAS_SERVICE_OK", 0);\r
199 /**\r
200  * phpCAS::service() error code when the PT could not retrieve because\r
201  * the CAS server did not respond.\r
202  */\r
203 define("PHPCAS_SERVICE_PT_NO_SERVER_RESPONSE", 1);\r
204 /**\r
205  * phpCAS::service() error code when the PT could not retrieve because\r
206  * the response of the CAS server was ill-formed.\r
207  */\r
208 define("PHPCAS_SERVICE_PT_BAD_SERVER_RESPONSE", 2);\r
209 /**\r
210  * phpCAS::service() error code when the PT could not retrieve because\r
211  * the CAS server did not want to.\r
212  */\r
213 define("PHPCAS_SERVICE_PT_FAILURE", 3);\r
214 /**\r
215  * phpCAS::service() error code when the service was not available.\r
216  */\r
217 define("PHPCAS_SERVICE_NOT AVAILABLE", 4);\r
218 \r
219 /** @} */\r
220 // ------------------------------------------------------------------------\r
221 //  LANGUAGES\r
222 // ------------------------------------------------------------------------\r
223 /**\r
224  * @addtogroup publicLang\r
225  * @{\r
226  */\r
227 \r
228 define("PHPCAS_LANG_ENGLISH", 'english');\r
229 define("PHPCAS_LANG_FRENCH", 'french');\r
230 define("PHPCAS_LANG_GREEK", 'greek');\r
231 define("PHPCAS_LANG_GERMAN", 'german');\r
232 define("PHPCAS_LANG_JAPANESE", 'japanese');\r
233 define("PHPCAS_LANG_SPANISH", 'spanish');\r
234 define("PHPCAS_LANG_CATALAN", 'catalan');\r
235 \r
236 /** @} */\r
237 \r
238 /**\r
239  * @addtogroup internalLang\r
240  * @{\r
241  */\r
242 \r
243 /**\r
244  * phpCAS default language (when phpCAS::setLang() is not used)\r
245  */\r
246 define("PHPCAS_LANG_DEFAULT", PHPCAS_LANG_ENGLISH);\r
247 \r
248 /** @} */\r
249 // ------------------------------------------------------------------------\r
250 //  DEBUG\r
251 // ------------------------------------------------------------------------\r
252 /**\r
253  * @addtogroup publicDebug\r
254  * @{\r
255  */\r
256 \r
257 /**\r
258  * The default directory for the debug file under Unix.\r
259  */\r
260 define('DEFAULT_DEBUG_DIR', '/tmp/');\r
261 \r
262 /** @} */\r
263 // ------------------------------------------------------------------------\r
264 //  MISC\r
265 // ------------------------------------------------------------------------\r
266 /**\r
267  * @addtogroup internalMisc\r
268  * @{\r
269  */\r
270 \r
271 /**\r
272  * This global variable is used by the interface class phpCAS.\r
273  *\r
274  * @hideinitializer\r
275  */\r
276 $GLOBALS['PHPCAS_CLIENT'] = null;\r
277 \r
278 /**\r
279  * This global variable is used to store where the initializer is called from \r
280  * (to print a comprehensive error in case of multiple calls).\r
281  *\r
282  * @hideinitializer\r
283  */\r
284 $GLOBALS['PHPCAS_INIT_CALL'] = array (\r
285         'done' => FALSE,\r
286         'file' => '?',\r
287         'line' => -1,\r
288         'method' => '?'\r
289 );\r
290 \r
291 /**\r
292  * This global variable is used to store where the method checking\r
293  * the authentication is called from (to print comprehensive errors)\r
294  *\r
295  * @hideinitializer\r
296  */\r
297 $GLOBALS['PHPCAS_AUTH_CHECK_CALL'] = array (\r
298         'done' => FALSE,\r
299         'file' => '?',\r
300         'line' => -1,\r
301         'method' => '?',\r
302         'result' => FALSE\r
303 );\r
304 \r
305 /**\r
306  * This global variable is used to store phpCAS debug mode.\r
307  *\r
308  * @hideinitializer\r
309  */\r
310 $GLOBALS['PHPCAS_DEBUG'] = array (\r
311         'filename' => FALSE,\r
312         'indent' => 0,\r
313         'unique_id' => ''\r
314 );\r
315 \r
316 /** @} */\r
317 \r
318 // ########################################################################\r
319 //  CLIENT CLASS\r
320 // ########################################################################\r
321 \r
322 // include client class\r
323 include_once (dirname(__FILE__) . '/CAS/client.php');\r
324 \r
325 // ########################################################################\r
326 //  INTERFACE CLASS\r
327 // ########################################################################\r
328 \r
329 /**\r
330  * @class phpCAS\r
331  * The phpCAS class is a simple container for the phpCAS library. It provides CAS\r
332  * authentication for web applications written in PHP.\r
333  *\r
334  * @ingroup public\r
335  * @author Pascal Aubry <pascal.aubry at univ-rennes1.fr>\r
336  *\r
337  * \internal All its methods access the same object ($PHPCAS_CLIENT, declared \r
338  * at the end of CAS/client.php).\r
339  */\r
340 \r
341 class phpCAS {\r
342 \r
343         // ########################################################################\r
344         //  INITIALIZATION\r
345         // ########################################################################\r
346 \r
347         /**\r
348          * @addtogroup publicInit\r
349          * @{\r
350          */\r
351 \r
352         /**\r
353          * phpCAS client initializer.\r
354          * @note Only one of the phpCAS::client() and phpCAS::proxy functions should be\r
355          * called, only once, and before all other methods (except phpCAS::getVersion()\r
356          * and phpCAS::setDebug()).\r
357          *\r
358          * @param $server_version the version of the CAS server\r
359          * @param $server_hostname the hostname of the CAS server\r
360          * @param $server_port the port the CAS server is running on\r
361          * @param $server_uri the URI the CAS server is responding on\r
362          * @param $start_session Have phpCAS start PHP sessions (default true)\r
363          *\r
364          * @return a newly created CASClient object\r
365          */\r
366         function client($server_version, $server_hostname, $server_port, $server_uri, $start_session = true) {\r
367                 global $PHPCAS_CLIENT, $PHPCAS_INIT_CALL;\r
368 \r
369                 phpCAS :: traceBegin();\r
370                 if (is_object($PHPCAS_CLIENT)) {\r
371                         phpCAS :: error($PHPCAS_INIT_CALL['method'] . '() has already been called (at ' . $PHPCAS_INIT_CALL['file'] . ':' . $PHPCAS_INIT_CALL['line'] . ')');\r
372                 }\r
373                 if (gettype($server_version) != 'string') {\r
374                         phpCAS :: error('type mismatched for parameter $server_version (should be `string\')');\r
375                 }\r
376                 if (gettype($server_hostname) != 'string') {\r
377                         phpCAS :: error('type mismatched for parameter $server_hostname (should be `string\')');\r
378                 }\r
379                 if (gettype($server_port) != 'integer') {\r
380                         phpCAS :: error('type mismatched for parameter $server_port (should be `integer\')');\r
381                 }\r
382                 if (gettype($server_uri) != 'string') {\r
383                         phpCAS :: error('type mismatched for parameter $server_uri (should be `string\')');\r
384                 }\r
385 \r
386                 // store where the initializer is called from\r
387                 $dbg = phpCAS :: backtrace();\r
388                 $PHPCAS_INIT_CALL = array (\r
389                         'done' => TRUE,\r
390                         'file' => $dbg[0]['file'],\r
391                         'line' => $dbg[0]['line'],\r
392                         'method' => __CLASS__ . '::' . __FUNCTION__\r
393                 );\r
394 \r
395                 // initialize the global object $PHPCAS_CLIENT\r
396                 $PHPCAS_CLIENT = new CASClient($server_version, FALSE /*proxy*/\r
397                 , $server_hostname, $server_port, $server_uri, $start_session);\r
398                 phpCAS :: traceEnd();\r
399         }\r
400 \r
401         /**\r
402          * phpCAS proxy initializer.\r
403          * @note Only one of the phpCAS::client() and phpCAS::proxy functions should be\r
404          * called, only once, and before all other methods (except phpCAS::getVersion()\r
405          * and phpCAS::setDebug()).\r
406          *\r
407          * @param $server_version the version of the CAS server\r
408          * @param $server_hostname the hostname of the CAS server\r
409          * @param $server_port the port the CAS server is running on\r
410          * @param $server_uri the URI the CAS server is responding on\r
411          * @param $start_session Have phpCAS start PHP sessions (default true)\r
412          *\r
413          * @return a newly created CASClient object\r
414          */\r
415         function proxy($server_version, $server_hostname, $server_port, $server_uri, $start_session = true) {\r
416                 global $PHPCAS_CLIENT, $PHPCAS_INIT_CALL;\r
417 \r
418                 phpCAS :: traceBegin();\r
419                 if (is_object($PHPCAS_CLIENT)) {\r
420                         phpCAS :: error($PHPCAS_INIT_CALL['method'] . '() has already been called (at ' . $PHPCAS_INIT_CALL['file'] . ':' . $PHPCAS_INIT_CALL['line'] . ')');\r
421                 }\r
422                 if (gettype($server_version) != 'string') {\r
423                         phpCAS :: error('type mismatched for parameter $server_version (should be `string\')');\r
424                 }\r
425                 if (gettype($server_hostname) != 'string') {\r
426                         phpCAS :: error('type mismatched for parameter $server_hostname (should be `string\')');\r
427                 }\r
428                 if (gettype($server_port) != 'integer') {\r
429                         phpCAS :: error('type mismatched for parameter $server_port (should be `integer\')');\r
430                 }\r
431                 if (gettype($server_uri) != 'string') {\r
432                         phpCAS :: error('type mismatched for parameter $server_uri (should be `string\')');\r
433                 }\r
434 \r
435                 // store where the initialzer is called from\r
436                 $dbg = phpCAS :: backtrace();\r
437                 $PHPCAS_INIT_CALL = array (\r
438                         'done' => TRUE,\r
439                         'file' => $dbg[0]['file'],\r
440                         'line' => $dbg[0]['line'],\r
441                         'method' => __CLASS__ . '::' . __FUNCTION__\r
442                 );\r
443 \r
444                 // initialize the global object $PHPCAS_CLIENT\r
445                 $PHPCAS_CLIENT = new CASClient($server_version, TRUE /*proxy*/\r
446                 , $server_hostname, $server_port, $server_uri, $start_session);\r
447                 phpCAS :: traceEnd();\r
448         }\r
449 \r
450         /** @} */\r
451         // ########################################################################\r
452         //  DEBUGGING\r
453         // ########################################################################\r
454 \r
455         /**\r
456          * @addtogroup publicDebug\r
457          * @{\r
458          */\r
459 \r
460         /**\r
461          * Set/unset debug mode\r
462          *\r
463          * @param $filename the name of the file used for logging, or FALSE to stop debugging.\r
464          */\r
465         function setDebug($filename = '') {\r
466                 global $PHPCAS_DEBUG;\r
467 \r
468                 if ($filename != FALSE && gettype($filename) != 'string') {\r
469                         phpCAS :: error('type mismatched for parameter $dbg (should be FALSE or the name of the log file)');\r
470                 }\r
471 \r
472                 if (empty ($filename)) {\r
473                         if (preg_match('/^Win.*/', getenv('OS'))) {\r
474                                 if (isset ($_ENV['TMP'])) {\r
475                                         $debugDir = $_ENV['TMP'] . '/';\r
476                                 } else\r
477                                         if (isset ($_ENV['TEMP'])) {\r
478                                                 $debugDir = $_ENV['TEMP'] . '/';\r
479                                         } else {\r
480                                                 $debugDir = '';\r
481                                         }\r
482                         } else {\r
483                                 $debugDir = DEFAULT_DEBUG_DIR;\r
484                         }\r
485                         $filename = $debugDir . 'phpCAS.log';\r
486                 }\r
487 \r
488                 if (empty ($PHPCAS_DEBUG['unique_id'])) {\r
489                         $PHPCAS_DEBUG['unique_id'] = substr(strtoupper(md5(uniqid(''))), 0, 4);\r
490                 }\r
491 \r
492                 $PHPCAS_DEBUG['filename'] = $filename;\r
493 \r
494                 phpCAS :: trace('START phpCAS-' . PHPCAS_VERSION . ' ******************');\r
495         }\r
496 \r
497         /** @} */\r
498         /**\r
499          * @addtogroup internalDebug\r
500          * @{\r
501          */\r
502 \r
503         /**\r
504          * This method is a wrapper for debug_backtrace() that is not available \r
505          * in all PHP versions (>= 4.3.0 only)\r
506          */\r
507         function backtrace() {\r
508                 if (function_exists('debug_backtrace')) {\r
509                         return debug_backtrace();\r
510                 } else {\r
511                         // poor man's hack ... but it does work ...\r
512                         return array ();\r
513                 }\r
514         }\r
515 \r
516         /**\r
517          * Logs a string in debug mode.\r
518          *\r
519          * @param $str the string to write\r
520          *\r
521          * @private\r
522          */\r
523         function log($str) {\r
524                 $indent_str = ".";\r
525                 global $PHPCAS_DEBUG;\r
526 \r
527                 if ($PHPCAS_DEBUG['filename']) {\r
528                         for ($i = 0; $i < $PHPCAS_DEBUG['indent']; $i++) {\r
529                                 $indent_str .= '|    ';\r
530                         }\r
531                         error_log($PHPCAS_DEBUG['unique_id'] . ' ' . $indent_str . $str . "\n", 3, $PHPCAS_DEBUG['filename']);\r
532                 }\r
533 \r
534         }\r
535 \r
536         /**\r
537          * This method is used by interface methods to print an error and where the function\r
538          * was originally called from.\r
539          *\r
540          * @param $msg the message to print\r
541          *\r
542          * @private\r
543          */\r
544         function error($msg) {\r
545                 $dbg = phpCAS :: backtrace();\r
546                 $function = '?';\r
547                 $file = '?';\r
548                 $line = '?';\r
549                 if (is_array($dbg)) {\r
550                         for ($i = 1; $i < sizeof($dbg); $i++) {\r
551                                 if (is_array($dbg[$i])) {\r
552                                         if ($dbg[$i]['class'] == __CLASS__) {\r
553                                                 $function = $dbg[$i]['function'];\r
554                                                 $file = $dbg[$i]['file'];\r
555                                                 $line = $dbg[$i]['line'];\r
556                                         }\r
557                                 }\r
558                         }\r
559                 }\r
560                 echo "<br />\n<b>phpCAS error</b>: <font color=\"FF0000\"><b>" . __CLASS__ . "::" . $function . '(): ' . htmlentities($msg) . "</b></font> in <b>" . $file . "</b> on line <b>" . $line . "</b><br />\n";\r
561                 phpCAS :: trace($msg);\r
562                 phpCAS :: traceExit();\r
563                 exit ();\r
564         }\r
565 \r
566         /**\r
567          * This method is used to log something in debug mode.\r
568          */\r
569         function trace($str) {\r
570                 $dbg = phpCAS :: backtrace();\r
571                 phpCAS :: log($str . ' [' . basename($dbg[1]['file']) . ':' . $dbg[1]['line'] . ']');\r
572         }\r
573 \r
574         /**\r
575          * This method is used to indicate the start of the execution of a function in debug mode.\r
576          */\r
577         function traceBegin() {\r
578                 global $PHPCAS_DEBUG;\r
579 \r
580                 $dbg = phpCAS :: backtrace();\r
581                 $str = '=> ';\r
582                 if (!empty ($dbg[2]['class'])) {\r
583                         $str .= $dbg[2]['class'] . '::';\r
584                 }\r
585                 $str .= $dbg[2]['function'] . '(';\r
586                 if (is_array($dbg[2]['args'])) {\r
587                         foreach ($dbg[2]['args'] as $index => $arg) {\r
588                                 if ($index != 0) {\r
589                                         $str .= ', ';\r
590                                 }\r
591                                 $str .= str_replace("\n", "", var_export($arg, TRUE));\r
592                         }\r
593                 }\r
594                 $str .= ') [' . basename($dbg[2]['file']) . ':' . $dbg[2]['line'] . ']';\r
595                 phpCAS :: log($str);\r
596                 $PHPCAS_DEBUG['indent']++;\r
597         }\r
598 \r
599         /**\r
600          * This method is used to indicate the end of the execution of a function in debug mode.\r
601          *\r
602          * @param $res the result of the function\r
603          */\r
604         function traceEnd($res = '') {\r
605                 global $PHPCAS_DEBUG;\r
606 \r
607                 $PHPCAS_DEBUG['indent']--;\r
608                 $dbg = phpCAS :: backtrace();\r
609                 $str = '';\r
610                 $str .= '<= ' . str_replace("\n", "", var_export($res, TRUE));\r
611                 phpCAS :: log($str);\r
612         }\r
613 \r
614         /**\r
615          * This method is used to indicate the end of the execution of the program\r
616          */\r
617         function traceExit() {\r
618                 global $PHPCAS_DEBUG;\r
619 \r
620                 phpCAS :: log('exit()');\r
621                 while ($PHPCAS_DEBUG['indent'] > 0) {\r
622                         phpCAS :: log('-');\r
623                         $PHPCAS_DEBUG['indent']--;\r
624                 }\r
625         }\r
626 \r
627         /** @} */\r
628         // ########################################################################\r
629         //  INTERNATIONALIZATION\r
630         // ########################################################################\r
631         /**\r
632          * @addtogroup publicLang\r
633          * @{\r
634          */\r
635 \r
636         /**\r
637          * This method is used to set the language used by phpCAS. \r
638          * @note Can be called only once.\r
639          *\r
640          * @param $lang a string representing the language.\r
641          *\r
642          * @sa PHPCAS_LANG_FRENCH, PHPCAS_LANG_ENGLISH\r
643          */\r
644         function setLang($lang) {\r
645                 global $PHPCAS_CLIENT;\r
646                 if (!is_object($PHPCAS_CLIENT)) {\r
647                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
648                 }\r
649                 if (gettype($lang) != 'string') {\r
650                         phpCAS :: error('type mismatched for parameter $lang (should be `string\')');\r
651                 }\r
652                 $PHPCAS_CLIENT->setLang($lang);\r
653         }\r
654 \r
655         /** @} */\r
656         // ########################################################################\r
657         //  VERSION\r
658         // ########################################################################\r
659         /**\r
660          * @addtogroup public\r
661          * @{\r
662          */\r
663 \r
664         /**\r
665          * This method returns the phpCAS version.\r
666          *\r
667          * @return the phpCAS version.\r
668          */\r
669         function getVersion() {\r
670                 return PHPCAS_VERSION;\r
671         }\r
672 \r
673         /** @} */\r
674         // ########################################################################\r
675         //  HTML OUTPUT\r
676         // ########################################################################\r
677         /**\r
678          * @addtogroup publicOutput\r
679          * @{\r
680          */\r
681 \r
682         /**\r
683          * This method sets the HTML header used for all outputs.\r
684          *\r
685          * @param $header the HTML header.\r
686          */\r
687         function setHTMLHeader($header) {\r
688                 global $PHPCAS_CLIENT;\r
689                 if (!is_object($PHPCAS_CLIENT)) {\r
690                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
691                 }\r
692                 if (gettype($header) != 'string') {\r
693                         phpCAS :: error('type mismatched for parameter $header (should be `string\')');\r
694                 }\r
695                 $PHPCAS_CLIENT->setHTMLHeader($header);\r
696         }\r
697 \r
698         /**\r
699          * This method sets the HTML footer used for all outputs.\r
700          *\r
701          * @param $footer the HTML footer.\r
702          */\r
703         function setHTMLFooter($footer) {\r
704                 global $PHPCAS_CLIENT;\r
705                 if (!is_object($PHPCAS_CLIENT)) {\r
706                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
707                 }\r
708                 if (gettype($footer) != 'string') {\r
709                         phpCAS :: error('type mismatched for parameter $footer (should be `string\')');\r
710                 }\r
711                 $PHPCAS_CLIENT->setHTMLFooter($footer);\r
712         }\r
713 \r
714         /** @} */\r
715         // ########################################################################\r
716         //  PGT STORAGE\r
717         // ########################################################################\r
718         /**\r
719          * @addtogroup publicPGTStorage\r
720          * @{\r
721          */\r
722 \r
723         /**\r
724          * This method is used to tell phpCAS to store the response of the\r
725          * CAS server to PGT requests onto the filesystem. \r
726          *\r
727          * @param $format the format used to store the PGT's (`plain' and `xml' allowed)\r
728          * @param $path the path where the PGT's should be stored\r
729          */\r
730         function setPGTStorageFile($format = '', $path = '') {\r
731                 global $PHPCAS_CLIENT, $PHPCAS_AUTH_CHECK_CALL;\r
732 \r
733                 phpCAS :: traceBegin();\r
734                 if (!is_object($PHPCAS_CLIENT)) {\r
735                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
736                 }\r
737                 if (!$PHPCAS_CLIENT->isProxy()) {\r
738                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
739                 }\r
740                 if ($PHPCAS_AUTH_CHECK_CALL['done']) {\r
741                         phpCAS :: error('this method should only be called before ' . $PHPCAS_AUTH_CHECK_CALL['method'] . '() (called at ' . $PHPCAS_AUTH_CHECK_CALL['file'] . ':' . $PHPCAS_AUTH_CHECK_CALL['line'] . ')');\r
742                 }\r
743                 if (gettype($format) != 'string') {\r
744                         phpCAS :: error('type mismatched for parameter $format (should be `string\')');\r
745                 }\r
746                 if (gettype($path) != 'string') {\r
747                         phpCAS :: error('type mismatched for parameter $format (should be `string\')');\r
748                 }\r
749                 $PHPCAS_CLIENT->setPGTStorageFile($format, $path);\r
750                 phpCAS :: traceEnd();\r
751         }\r
752 \r
753         /**\r
754          * This method is used to tell phpCAS to store the response of the\r
755          * CAS server to PGT requests into a database. \r
756          * @note The connection to the database is done only when needed. \r
757          * As a consequence, bad parameters are detected only when \r
758          * initializing PGT storage, except in debug mode.\r
759          *\r
760          * @param $user the user to access the data with\r
761          * @param $password the user's password\r
762          * @param $database_type the type of the database hosting the data\r
763          * @param $hostname the server hosting the database\r
764          * @param $port the port the server is listening on\r
765          * @param $database the name of the database\r
766          * @param $table the name of the table storing the data\r
767          */\r
768         function setPGTStorageDB($user, $password, $database_type = '', $hostname = '', $port = 0, $database = '', $table = '') {\r
769                 global $PHPCAS_CLIENT, $PHPCAS_AUTH_CHECK_CALL;\r
770 \r
771                 phpCAS :: traceBegin();\r
772                 if (!is_object($PHPCAS_CLIENT)) {\r
773                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
774                 }\r
775                 if (!$PHPCAS_CLIENT->isProxy()) {\r
776                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
777                 }\r
778                 if ($PHPCAS_AUTH_CHECK_CALL['done']) {\r
779                         phpCAS :: error('this method should only be called before ' . $PHPCAS_AUTH_CHECK_CALL['method'] . '() (called at ' . $PHPCAS_AUTH_CHECK_CALL['file'] . ':' . $PHPCAS_AUTH_CHECK_CALL['line'] . ')');\r
780                 }\r
781                 if (gettype($user) != 'string') {\r
782                         phpCAS :: error('type mismatched for parameter $user (should be `string\')');\r
783                 }\r
784                 if (gettype($password) != 'string') {\r
785                         phpCAS :: error('type mismatched for parameter $password (should be `string\')');\r
786                 }\r
787                 if (gettype($database_type) != 'string') {\r
788                         phpCAS :: error('type mismatched for parameter $database_type (should be `string\')');\r
789                 }\r
790                 if (gettype($hostname) != 'string') {\r
791                         phpCAS :: error('type mismatched for parameter $hostname (should be `string\')');\r
792                 }\r
793                 if (gettype($port) != 'integer') {\r
794                         phpCAS :: error('type mismatched for parameter $port (should be `integer\')');\r
795                 }\r
796                 if (gettype($database) != 'string') {\r
797                         phpCAS :: error('type mismatched for parameter $database (should be `string\')');\r
798                 }\r
799                 if (gettype($table) != 'string') {\r
800                         phpCAS :: error('type mismatched for parameter $table (should be `string\')');\r
801                 }\r
802                 $PHPCAS_CLIENT->setPGTStorageDB($user, $password, $database_type, $hostname, $port, $database, $table);\r
803                 phpCAS :: traceEnd();\r
804         }\r
805 \r
806         /** @} */\r
807         // ########################################################################\r
808         // ACCESS TO EXTERNAL SERVICES\r
809         // ########################################################################\r
810         /**\r
811          * @addtogroup publicServices\r
812          * @{\r
813          */\r
814 \r
815         /**\r
816          * This method is used to access an HTTP[S] service.\r
817          * \r
818          * @param $url the service to access.\r
819          * @param $err_code an error code Possible values are PHPCAS_SERVICE_OK (on\r
820          * success), PHPCAS_SERVICE_PT_NO_SERVER_RESPONSE, PHPCAS_SERVICE_PT_BAD_SERVER_RESPONSE,\r
821          * PHPCAS_SERVICE_PT_FAILURE, PHPCAS_SERVICE_NOT AVAILABLE.\r
822          * @param $output the output of the service (also used to give an error\r
823          * message on failure).\r
824          *\r
825          * @return TRUE on success, FALSE otherwise (in this later case, $err_code\r
826          * gives the reason why it failed and $output contains an error message).\r
827          */\r
828         function serviceWeb($url, & $err_code, & $output) {\r
829                 global $PHPCAS_CLIENT, $PHPCAS_AUTH_CHECK_CALL;\r
830 \r
831                 phpCAS :: traceBegin();\r
832                 if (!is_object($PHPCAS_CLIENT)) {\r
833                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
834                 }\r
835                 if (!$PHPCAS_CLIENT->isProxy()) {\r
836                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
837                 }\r
838                 if (!$PHPCAS_AUTH_CHECK_CALL['done']) {\r
839                         phpCAS :: error('this method should only be called after the programmer is sure the user has been authenticated (by calling ' . __CLASS__ . '::checkAuthentication() or ' . __CLASS__ . '::forceAuthentication()');\r
840                 }\r
841                 if (!$PHPCAS_AUTH_CHECK_CALL['result']) {\r
842                         phpCAS :: error('authentication was checked (by ' . $PHPCAS_AUTH_CHECK_CALL['method'] . '() at ' . $PHPCAS_AUTH_CHECK_CALL['file'] . ':' . $PHPCAS_AUTH_CHECK_CALL['line'] . ') but the method returned FALSE');\r
843                 }\r
844                 if (gettype($url) != 'string') {\r
845                         phpCAS :: error('type mismatched for parameter $url (should be `string\')');\r
846                 }\r
847 \r
848                 $res = $PHPCAS_CLIENT->serviceWeb($url, $err_code, $output);\r
849 \r
850                 phpCAS :: traceEnd($res);\r
851                 return $res;\r
852         }\r
853 \r
854         /**\r
855          * This method is used to access an IMAP/POP3/NNTP service.\r
856          * \r
857          * @param $url a string giving the URL of the service, including the mailing box\r
858          * for IMAP URLs, as accepted by imap_open().\r
859          * @param $service a string giving for CAS retrieve Proxy ticket\r
860          * @param $flags options given to imap_open().\r
861          * @param $err_code an error code Possible values are PHPCAS_SERVICE_OK (on\r
862          * success), PHPCAS_SERVICE_PT_NO_SERVER_RESPONSE, PHPCAS_SERVICE_PT_BAD_SERVER_RESPONSE,\r
863          * PHPCAS_SERVICE_PT_FAILURE, PHPCAS_SERVICE_NOT AVAILABLE.\r
864          * @param $err_msg an error message on failure\r
865          * @param $pt the Proxy Ticket (PT) retrieved from the CAS server to access the URL\r
866          * on success, FALSE on error).\r
867          *\r
868          * @return an IMAP stream on success, FALSE otherwise (in this later case, $err_code\r
869          * gives the reason why it failed and $err_msg contains an error message).\r
870          */\r
871         function serviceMail($url, $service, $flags, & $err_code, & $err_msg, & $pt) {\r
872                 global $PHPCAS_CLIENT, $PHPCAS_AUTH_CHECK_CALL;\r
873 \r
874                 phpCAS :: traceBegin();\r
875                 if (!is_object($PHPCAS_CLIENT)) {\r
876                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
877                 }\r
878                 if (!$PHPCAS_CLIENT->isProxy()) {\r
879                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
880                 }\r
881                 if (!$PHPCAS_AUTH_CHECK_CALL['done']) {\r
882                         phpCAS :: error('this method should only be called after the programmer is sure the user has been authenticated (by calling ' . __CLASS__ . '::checkAuthentication() or ' . __CLASS__ . '::forceAuthentication()');\r
883                 }\r
884                 if (!$PHPCAS_AUTH_CHECK_CALL['result']) {\r
885                         phpCAS :: error('authentication was checked (by ' . $PHPCAS_AUTH_CHECK_CALL['method'] . '() at ' . $PHPCAS_AUTH_CHECK_CALL['file'] . ':' . $PHPCAS_AUTH_CHECK_CALL['line'] . ') but the method returned FALSE');\r
886                 }\r
887                 if (gettype($url) != 'string') {\r
888                         phpCAS :: error('type mismatched for parameter $url (should be `string\')');\r
889                 }\r
890 \r
891                 if (gettype($flags) != 'integer') {\r
892                         phpCAS :: error('type mismatched for parameter $flags (should be `integer\')');\r
893                 }\r
894 \r
895                 $res = $PHPCAS_CLIENT->serviceMail($url, $service, $flags, $err_code, $err_msg, $pt);\r
896 \r
897                 phpCAS :: traceEnd($res);\r
898                 return $res;\r
899         }\r
900 \r
901         /** @} */\r
902         // ########################################################################\r
903         //  AUTHENTICATION\r
904         // ########################################################################\r
905         /**\r
906          * @addtogroup publicAuth\r
907          * @{\r
908          */\r
909 \r
910         /**\r
911          * Set the times authentication will be cached before really accessing the CAS server in gateway mode: \r
912          * - -1: check only once, and then never again (until you pree login)\r
913          * - 0: always check\r
914          * - n: check every "n" time\r
915          *\r
916          * @param $n an integer.\r
917          */\r
918         function setCacheTimesForAuthRecheck($n) {\r
919                 global $PHPCAS_CLIENT;\r
920                 if (!is_object($PHPCAS_CLIENT)) {\r
921                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
922                 }\r
923                 if (gettype($n) != 'integer') {\r
924                         phpCAS :: error('type mismatched for parameter $header (should be `string\')');\r
925                 }\r
926                 $PHPCAS_CLIENT->setCacheTimesForAuthRecheck($n);\r
927         }\r
928 \r
929         /**\r
930          * This method is called to check if the user is authenticated (use the gateway feature).\r
931          * @return TRUE when the user is authenticated; otherwise FALSE.\r
932          */\r
933         function checkAuthentication() {\r
934                 global $PHPCAS_CLIENT, $PHPCAS_AUTH_CHECK_CALL;\r
935 \r
936                 phpCAS :: traceBegin();\r
937                 if (!is_object($PHPCAS_CLIENT)) {\r
938                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
939                 }\r
940 \r
941                 $auth = $PHPCAS_CLIENT->checkAuthentication();\r
942 \r
943                 // store where the authentication has been checked and the result\r
944                 $dbg = phpCAS :: backtrace();\r
945                 $PHPCAS_AUTH_CHECK_CALL = array (\r
946                         'done' => TRUE,\r
947                         'file' => $dbg[0]['file'],\r
948                         'line' => $dbg[0]['line'],\r
949                         'method' => __CLASS__ . '::' . __FUNCTION__,\r
950                         'result' => $auth\r
951                 );\r
952                 phpCAS :: traceEnd($auth);\r
953                 return $auth;\r
954         }\r
955 \r
956         /**\r
957          * This method is called to force authentication if the user was not already \r
958          * authenticated. If the user is not authenticated, halt by redirecting to \r
959          * the CAS server.\r
960          */\r
961         function forceAuthentication() {\r
962                 global $PHPCAS_CLIENT, $PHPCAS_AUTH_CHECK_CALL;\r
963 \r
964                 phpCAS :: traceBegin();\r
965                 if (!is_object($PHPCAS_CLIENT)) {\r
966                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
967                 }\r
968 \r
969                 $auth = $PHPCAS_CLIENT->forceAuthentication();\r
970 \r
971                 // store where the authentication has been checked and the result\r
972                 $dbg = phpCAS :: backtrace();\r
973                 $PHPCAS_AUTH_CHECK_CALL = array (\r
974                         'done' => TRUE,\r
975                         'file' => $dbg[0]['file'],\r
976                         'line' => $dbg[0]['line'],\r
977                         'method' => __CLASS__ . '::' . __FUNCTION__,\r
978                         'result' => $auth\r
979                 );\r
980 \r
981                 if (!$auth) {\r
982                         phpCAS :: trace('user is not authenticated, redirecting to the CAS server');\r
983                         $PHPCAS_CLIENT->forceAuthentication();\r
984                 } else {\r
985                         phpCAS :: trace('no need to authenticate (user `' . phpCAS :: getUser() . '\' is already authenticated)');\r
986                 }\r
987 \r
988                 phpCAS :: traceEnd();\r
989                 return $auth;\r
990         }\r
991 \r
992         /**\r
993          * This method is called to renew the authentication.\r
994          **/\r
995         function renewAuthentication() {\r
996                 global $PHPCAS_CLIENT, $PHPCAS_AUTH_CHECK_CALL;\r
997 \r
998                 phpCAS :: traceBegin();\r
999                 if (!is_object($PHPCAS_CLIENT)) {\r
1000                         phpCAS :: error('this method should not be called before' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
1001                 }\r
1002 \r
1003                 // store where the authentication has been checked and the result\r
1004                 $dbg = phpCAS :: backtrace();\r
1005                 $PHPCAS_AUTH_CHECK_CALL = array (\r
1006                         'done' => TRUE,\r
1007                         'file' => $dbg[0]['file'],\r
1008                         'line' => $dbg[0]['line'],\r
1009                         'method' => __CLASS__ . '::' . __FUNCTION__,\r
1010                         'result' => $auth\r
1011                 );\r
1012 \r
1013                 $PHPCAS_CLIENT->renewAuthentication();\r
1014                 phpCAS :: traceEnd();\r
1015         }\r
1016 \r
1017         /**\r
1018          * This method has been left from version 0.4.1 for compatibility reasons.\r
1019          */\r
1020         function authenticate() {\r
1021                 phpCAS :: error('this method is deprecated. You should use ' . __CLASS__ . '::forceAuthentication() instead');\r
1022         }\r
1023 \r
1024         /**\r
1025          * This method is called to check if the user is authenticated (previously or by\r
1026          * tickets given in the URL).\r
1027          *\r
1028          * @return TRUE when the user is authenticated.\r
1029          */\r
1030         function isAuthenticated() {\r
1031                 global $PHPCAS_CLIENT, $PHPCAS_AUTH_CHECK_CALL;\r
1032 \r
1033                 phpCAS :: traceBegin();\r
1034                 if (!is_object($PHPCAS_CLIENT)) {\r
1035                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
1036                 }\r
1037 \r
1038                 // call the isAuthenticated method of the global $PHPCAS_CLIENT object\r
1039                 $auth = $PHPCAS_CLIENT->isAuthenticated();\r
1040 \r
1041                 // store where the authentication has been checked and the result\r
1042                 $dbg = phpCAS :: backtrace();\r
1043                 $PHPCAS_AUTH_CHECK_CALL = array (\r
1044                         'done' => TRUE,\r
1045                         'file' => $dbg[0]['file'],\r
1046                         'line' => $dbg[0]['line'],\r
1047                         'method' => __CLASS__ . '::' . __FUNCTION__,\r
1048                         'result' => $auth\r
1049                 );\r
1050                 phpCAS :: traceEnd($auth);\r
1051                 return $auth;\r
1052         }\r
1053 \r
1054         /**\r
1055          * Checks whether authenticated based on $_SESSION. Useful to avoid\r
1056          * server calls.\r
1057          * @return true if authenticated, false otherwise.\r
1058          * @since 0.4.22 by Brendan Arnold\r
1059          */\r
1060         function isSessionAuthenticated() {\r
1061                 global $PHPCAS_CLIENT;\r
1062                 if (!is_object($PHPCAS_CLIENT)) {\r
1063                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
1064                 }\r
1065                 return ($PHPCAS_CLIENT->isSessionAuthenticated());\r
1066         }\r
1067 \r
1068         /**\r
1069          * This method returns the CAS user's login name.\r
1070          * @warning should not be called only after phpCAS::forceAuthentication()\r
1071          * or phpCAS::checkAuthentication().\r
1072          *\r
1073          * @return the login name of the authenticated user\r
1074          */\r
1075         function getUser() {\r
1076                 global $PHPCAS_CLIENT, $PHPCAS_AUTH_CHECK_CALL;\r
1077                 if (!is_object($PHPCAS_CLIENT)) {\r
1078                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
1079                 }\r
1080                 if (!$PHPCAS_AUTH_CHECK_CALL['done']) {\r
1081                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::forceAuthentication() or ' . __CLASS__ . '::isAuthenticated()');\r
1082                 }\r
1083                 if (!$PHPCAS_AUTH_CHECK_CALL['result']) {\r
1084                         phpCAS :: error('authentication was checked (by ' . $PHPCAS_AUTH_CHECK_CALL['method'] . '() at ' . $PHPCAS_AUTH_CHECK_CALL['file'] . ':' . $PHPCAS_AUTH_CHECK_CALL['line'] . ') but the method returned FALSE');\r
1085                 }\r
1086                 return $PHPCAS_CLIENT->getUser();\r
1087         }\r
1088 \r
1089         /**\r
1090          * This method returns the CAS user's login name.\r
1091          * @warning should not be called only after phpCAS::forceAuthentication()\r
1092          * or phpCAS::checkAuthentication().\r
1093          *\r
1094          * @return the login name of the authenticated user\r
1095          */\r
1096         function getAttributes() {\r
1097                 global $PHPCAS_CLIENT, $PHPCAS_AUTH_CHECK_CALL;\r
1098                 if (!is_object($PHPCAS_CLIENT)) {\r
1099                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
1100                 }\r
1101                 if (!$PHPCAS_AUTH_CHECK_CALL['done']) {\r
1102                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::forceAuthentication() or ' . __CLASS__ . '::isAuthenticated()');\r
1103                 }\r
1104                 if (!$PHPCAS_AUTH_CHECK_CALL['result']) {\r
1105                         phpCAS :: error('authentication was checked (by ' . $PHPCAS_AUTH_CHECK_CALL['method'] . '() at ' . $PHPCAS_AUTH_CHECK_CALL['file'] . ':' . $PHPCAS_AUTH_CHECK_CALL['line'] . ') but the method returned FALSE');\r
1106                 }\r
1107                 return $PHPCAS_CLIENT->getAttributes();\r
1108         }\r
1109         /**\r
1110          * Handle logout requests.\r
1111          */\r
1112         function handleLogoutRequests($check_client = true, $allowed_clients = false) {\r
1113                 global $PHPCAS_CLIENT;\r
1114                 if (!is_object($PHPCAS_CLIENT)) {\r
1115                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
1116                 }\r
1117                 return ($PHPCAS_CLIENT->handleLogoutRequests($check_client, $allowed_clients));\r
1118         }\r
1119 \r
1120         /**\r
1121          * This method returns the URL to be used to login.\r
1122          * or phpCAS::isAuthenticated().\r
1123          *\r
1124          * @return the login name of the authenticated user\r
1125          */\r
1126         function getServerLoginURL() {\r
1127                 global $PHPCAS_CLIENT;\r
1128                 if (!is_object($PHPCAS_CLIENT)) {\r
1129                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
1130                 }\r
1131                 return $PHPCAS_CLIENT->getServerLoginURL();\r
1132         }\r
1133 \r
1134         /**\r
1135          * Set the login URL of the CAS server.\r
1136          * @param $url the login URL\r
1137          * @since 0.4.21 by Wyman Chan\r
1138          */\r
1139         function setServerLoginURL($url = '') {\r
1140                 global $PHPCAS_CLIENT;\r
1141                 phpCAS :: traceBegin();\r
1142                 if (!is_object($PHPCAS_CLIENT)) {\r
1143                         phpCAS :: error('this method should only be called after\r
1144                                                         ' . __CLASS__ . '::client()');\r
1145                 }\r
1146                 if (gettype($url) != 'string') {\r
1147                         phpCAS :: error('type mismatched for parameter $url (should be\r
1148                                                 `string\')');\r
1149                 }\r
1150                 $PHPCAS_CLIENT->setServerLoginURL($url);\r
1151                 phpCAS :: traceEnd();\r
1152         }\r
1153 \r
1154         /**\r
1155          * Set the serviceValidate URL of the CAS server.\r
1156          * Used only in CAS 1.0 validations\r
1157          * @param $url the serviceValidate URL\r
1158          * @since 1.1.0 by Joachim Fritschi\r
1159          */\r
1160         function setServerServiceValidateURL($url = '') {\r
1161                 global $PHPCAS_CLIENT;\r
1162                 phpCAS :: traceBegin();\r
1163                 if (!is_object($PHPCAS_CLIENT)) {\r
1164                         phpCAS :: error('this method should only be called after\r
1165                                                         ' . __CLASS__ . '::client()');\r
1166                 }\r
1167                 if (gettype($url) != 'string') {\r
1168                         phpCAS :: error('type mismatched for parameter $url (should be\r
1169                                                 `string\')');\r
1170                 }\r
1171                 $PHPCAS_CLIENT->setServerServiceValidateURL($url);\r
1172                 phpCAS :: traceEnd();\r
1173         }\r
1174 \r
1175         /**\r
1176          * Set the proxyValidate URL of the CAS server.\r
1177          * Used for all CAS 2.0 validations\r
1178          * @param $url the proxyValidate URL\r
1179          * @since 1.1.0 by Joachim Fritschi\r
1180          */\r
1181         function setServerProxyValidateURL($url = '') {\r
1182                 global $PHPCAS_CLIENT;\r
1183                 phpCAS :: traceBegin();\r
1184                 if (!is_object($PHPCAS_CLIENT)) {\r
1185                         phpCAS :: error('this method should only be called after\r
1186                                                         ' . __CLASS__ . '::client()');\r
1187                 }\r
1188                 if (gettype($url) != 'string') {\r
1189                         phpCAS :: error('type mismatched for parameter $url (should be\r
1190                                                 `string\')');\r
1191                 }\r
1192                 $PHPCAS_CLIENT->setServerProxyValidateURL($url);\r
1193                 phpCAS :: traceEnd();\r
1194         }\r
1195 \r
1196         /**\r
1197          * Set the samlValidate URL of the CAS server.\r
1198          * @param $url the samlValidate URL\r
1199          * @since 1.1.0 by Joachim Fritschi\r
1200          */\r
1201         function setServerSamlValidateURL($url = '') {\r
1202                 global $PHPCAS_CLIENT;\r
1203                 phpCAS :: traceBegin();\r
1204                 if (!is_object($PHPCAS_CLIENT)) {\r
1205                         phpCAS :: error('this method should only be called after\r
1206                                                         ' . __CLASS__ . '::client()');\r
1207                 }\r
1208                 if (gettype($url) != 'string') {\r
1209                         phpCAS :: error('type mismatched for parameter $url (should be\r
1210                                                 `string\')');\r
1211                 }\r
1212                 $PHPCAS_CLIENT->setServerSamlValidateURL($url);\r
1213                 phpCAS :: traceEnd();\r
1214         }\r
1215 \r
1216         /**\r
1217          * This method returns the URL to be used to login.\r
1218          * or phpCAS::isAuthenticated().\r
1219          *\r
1220          * @return the login name of the authenticated user\r
1221          */\r
1222         function getServerLogoutURL() {\r
1223                 global $PHPCAS_CLIENT;\r
1224                 if (!is_object($PHPCAS_CLIENT)) {\r
1225                         phpCAS :: error('this method should not be called before ' . __CLASS__ . '::client() or ' . __CLASS__ . '::proxy()');\r
1226                 }\r
1227                 return $PHPCAS_CLIENT->getServerLogoutURL();\r
1228         }\r
1229 \r
1230         /**\r
1231          * Set the logout URL of the CAS server.\r
1232          * @param $url the logout URL\r
1233          * @since 0.4.21 by Wyman Chan\r
1234          */\r
1235         function setServerLogoutURL($url = '') {\r
1236                 global $PHPCAS_CLIENT;\r
1237                 phpCAS :: traceBegin();\r
1238                 if (!is_object($PHPCAS_CLIENT)) {\r
1239                         phpCAS :: error('this method should only be called after\r
1240                                                         ' . __CLASS__ . '::client()');\r
1241                 }\r
1242                 if (gettype($url) != 'string') {\r
1243                         phpCAS :: error('type mismatched for parameter $url (should be\r
1244                                                 `string\')');\r
1245                 }\r
1246                 $PHPCAS_CLIENT->setServerLogoutURL($url);\r
1247                 phpCAS :: traceEnd();\r
1248         }\r
1249 \r
1250         /**\r
1251          * This method is used to logout from CAS.\r
1252          * @params $params an array that contains the optional url and service parameters that will be passed to the CAS server\r
1253          * @public\r
1254          */\r
1255         function logout($params = "") {\r
1256                 global $PHPCAS_CLIENT;\r
1257                 phpCAS :: traceBegin();\r
1258                 if (!is_object($PHPCAS_CLIENT)) {\r
1259                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::client() or' . __CLASS__ . '::proxy()');\r
1260                 }\r
1261                 $parsedParams = array ();\r
1262                 if ($params != "") {\r
1263                         if (is_string($params)) {\r
1264                                 phpCAS :: error('method `phpCAS::logout($url)\' is now deprecated, use `phpCAS::logoutWithUrl($url)\' instead');\r
1265                         }\r
1266                         if (!is_array($params)) {\r
1267                                 phpCAS :: error('type mismatched for parameter $params (should be `array\')');\r
1268                         }\r
1269                         foreach ($params as $key => $value) {\r
1270                                 if ($key != "service" && $key != "url") {\r
1271                                         phpCAS :: error('only `url\' and `service\' parameters are allowed for method `phpCAS::logout($params)\'');\r
1272                                 }\r
1273                                 $parsedParams[$key] = $value;\r
1274                         }\r
1275                 }\r
1276                 $PHPCAS_CLIENT->logout($parsedParams);\r
1277                 // never reached\r
1278                 phpCAS :: traceEnd();\r
1279         }\r
1280 \r
1281         /**\r
1282          * This method is used to logout from CAS. Halts by redirecting to the CAS server.\r
1283          * @param $service a URL that will be transmitted to the CAS server\r
1284          */\r
1285         function logoutWithRedirectService($service) {\r
1286                 global $PHPCAS_CLIENT;\r
1287                 phpCAS :: traceBegin();\r
1288                 if (!is_object($PHPCAS_CLIENT)) {\r
1289                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::client() or' . __CLASS__ . '::proxy()');\r
1290                 }\r
1291                 if (!is_string($service)) {\r
1292                         phpCAS :: error('type mismatched for parameter $service (should be `string\')');\r
1293                 }\r
1294                 $PHPCAS_CLIENT->logout(array (\r
1295                         "service" => $service\r
1296                 ));\r
1297                 // never reached\r
1298                 phpCAS :: traceEnd();\r
1299         }\r
1300 \r
1301         /**\r
1302          * This method is used to logout from CAS. Halts by redirecting to the CAS server.\r
1303          * @param $url a URL that will be transmitted to the CAS server\r
1304          */\r
1305         function logoutWithUrl($url) {\r
1306                 global $PHPCAS_CLIENT;\r
1307                 phpCAS :: traceBegin();\r
1308                 if (!is_object($PHPCAS_CLIENT)) {\r
1309                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::client() or' . __CLASS__ . '::proxy()');\r
1310                 }\r
1311                 if (!is_string($url)) {\r
1312                         phpCAS :: error('type mismatched for parameter $url (should be `string\')');\r
1313                 }\r
1314                 $PHPCAS_CLIENT->logout(array (\r
1315                         "url" => $url\r
1316                 ));\r
1317                 // never reached\r
1318                 phpCAS :: traceEnd();\r
1319         }\r
1320 \r
1321         /**\r
1322          * This method is used to logout from CAS. Halts by redirecting to the CAS server.\r
1323          * @param $service a URL that will be transmitted to the CAS server\r
1324          * @param $url a URL that will be transmitted to the CAS server\r
1325          */\r
1326         function logoutWithRedirectServiceAndUrl($service, $url) {\r
1327                 global $PHPCAS_CLIENT;\r
1328                 phpCAS :: traceBegin();\r
1329                 if (!is_object($PHPCAS_CLIENT)) {\r
1330                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::client() or' . __CLASS__ . '::proxy()');\r
1331                 }\r
1332                 if (!is_string($service)) {\r
1333                         phpCAS :: error('type mismatched for parameter $service (should be `string\')');\r
1334                 }\r
1335                 if (!is_string($url)) {\r
1336                         phpCAS :: error('type mismatched for parameter $url (should be `string\')');\r
1337                 }\r
1338                 $PHPCAS_CLIENT->logout(array (\r
1339                         "service" => $service,\r
1340                         "url" => $url\r
1341                 ));\r
1342                 // never reached\r
1343                 phpCAS :: traceEnd();\r
1344         }\r
1345 \r
1346         /**\r
1347          * Set the fixed URL that will be used by the CAS server to transmit the PGT.\r
1348          * When this method is not called, a phpCAS script uses its own URL for the callback.\r
1349          *\r
1350          * @param $url the URL\r
1351          */\r
1352         function setFixedCallbackURL($url = '') {\r
1353                 global $PHPCAS_CLIENT;\r
1354                 phpCAS :: traceBegin();\r
1355                 if (!is_object($PHPCAS_CLIENT)) {\r
1356                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
1357                 }\r
1358                 if (!$PHPCAS_CLIENT->isProxy()) {\r
1359                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
1360                 }\r
1361                 if (gettype($url) != 'string') {\r
1362                         phpCAS :: error('type mismatched for parameter $url (should be `string\')');\r
1363                 }\r
1364                 $PHPCAS_CLIENT->setCallbackURL($url);\r
1365                 phpCAS :: traceEnd();\r
1366         }\r
1367 \r
1368         /**\r
1369          * Set the fixed URL that will be set as the CAS service parameter. When this\r
1370          * method is not called, a phpCAS script uses its own URL.\r
1371          *\r
1372          * @param $url the URL\r
1373          */\r
1374         function setFixedServiceURL($url) {\r
1375                 global $PHPCAS_CLIENT;\r
1376                 phpCAS :: traceBegin();\r
1377                 if (!is_object($PHPCAS_CLIENT)) {\r
1378                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
1379                 }\r
1380                 if (gettype($url) != 'string') {\r
1381                         phpCAS :: error('type mismatched for parameter $url (should be `string\')');\r
1382                 }\r
1383                 $PHPCAS_CLIENT->setURL($url);\r
1384                 phpCAS :: traceEnd();\r
1385         }\r
1386 \r
1387         /**\r
1388          * Get the URL that is set as the CAS service parameter.\r
1389          */\r
1390         function getServiceURL() {\r
1391                 global $PHPCAS_CLIENT;\r
1392                 if (!is_object($PHPCAS_CLIENT)) {\r
1393                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
1394                 }\r
1395                 return ($PHPCAS_CLIENT->getURL());\r
1396         }\r
1397 \r
1398         /**\r
1399          * Retrieve a Proxy Ticket from the CAS server.\r
1400          */\r
1401         function retrievePT($target_service, & $err_code, & $err_msg) {\r
1402                 global $PHPCAS_CLIENT;\r
1403                 if (!is_object($PHPCAS_CLIENT)) {\r
1404                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::proxy()');\r
1405                 }\r
1406                 if (gettype($target_service) != 'string') {\r
1407                         phpCAS :: error('type mismatched for parameter $target_service(should be `string\')');\r
1408                 }\r
1409                 return ($PHPCAS_CLIENT->retrievePT($target_service, $err_code, $err_msg));\r
1410         }\r
1411 \r
1412         /**\r
1413          * Set the certificate of the CAS server.\r
1414          *\r
1415          * @param $cert the PEM certificate\r
1416          */\r
1417         function setCasServerCert($cert) {\r
1418                 global $PHPCAS_CLIENT;\r
1419                 phpCAS :: traceBegin();\r
1420                 if (!is_object($PHPCAS_CLIENT)) {\r
1421                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::client() or' . __CLASS__ . '::proxy()');\r
1422                 }\r
1423                 if (gettype($cert) != 'string') {\r
1424                         phpCAS :: error('type mismatched for parameter $cert (should be `string\')');\r
1425                 }\r
1426                 $PHPCAS_CLIENT->setCasServerCert($cert);\r
1427                 phpCAS :: traceEnd();\r
1428         }\r
1429 \r
1430         /**\r
1431          * Set the certificate of the CAS server CA.\r
1432          *\r
1433          * @param $cert the CA certificate\r
1434          */\r
1435         function setCasServerCACert($cert) {\r
1436                 global $PHPCAS_CLIENT;\r
1437                 phpCAS :: traceBegin();\r
1438                 if (!is_object($PHPCAS_CLIENT)) {\r
1439                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::client() or' . __CLASS__ . '::proxy()');\r
1440                 }\r
1441                 if (gettype($cert) != 'string') {\r
1442                         phpCAS :: error('type mismatched for parameter $cert (should be `string\')');\r
1443                 }\r
1444                 $PHPCAS_CLIENT->setCasServerCACert($cert);\r
1445                 phpCAS :: traceEnd();\r
1446         }\r
1447 \r
1448         /**\r
1449          * Set no SSL validation for the CAS server.\r
1450          */\r
1451         function setNoCasServerValidation() {\r
1452                 global $PHPCAS_CLIENT;\r
1453                 phpCAS :: traceBegin();\r
1454                 if (!is_object($PHPCAS_CLIENT)) {\r
1455                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::client() or' . __CLASS__ . '::proxy()');\r
1456                 }\r
1457                 $PHPCAS_CLIENT->setNoCasServerValidation();\r
1458                 phpCAS :: traceEnd();\r
1459         }\r
1460 \r
1461         /** @} */\r
1462 \r
1463         /**\r
1464          * Change CURL options.\r
1465          * CURL is used to connect through HTTPS to CAS server\r
1466          * @param $key the option key\r
1467          * @param $value the value to set\r
1468          */\r
1469         function setExtraCurlOption($key, $value) {\r
1470                 global $PHPCAS_CLIENT;\r
1471                 phpCAS :: traceBegin();\r
1472                 if (!is_object($PHPCAS_CLIENT)) {\r
1473                         phpCAS :: error('this method should only be called after ' . __CLASS__ . '::client() or' . __CLASS__ . '::proxy()');\r
1474                 }\r
1475                 $PHPCAS_CLIENT->setExtraCurlOption($key, $value);\r
1476                 phpCAS :: traceEnd();\r
1477         }\r
1478 \r
1479 }\r
1480 \r
1481 // ########################################################################\r
1482 // DOCUMENTATION\r
1483 // ########################################################################\r
1484 \r
1485 // ########################################################################\r
1486 //  MAIN PAGE\r
1487 \r
1488 /**\r
1489  * @mainpage\r
1490  *\r
1491  * The following pages only show the source documentation.\r
1492  *\r
1493  */\r
1494 \r
1495 // ########################################################################\r
1496 //  MODULES DEFINITION\r
1497 \r
1498 /** @defgroup public User interface */\r
1499 \r
1500 /** @defgroup publicInit Initialization\r
1501  *  @ingroup public */\r
1502 \r
1503 /** @defgroup publicAuth Authentication\r
1504  *  @ingroup public */\r
1505 \r
1506 /** @defgroup publicServices Access to external services\r
1507  *  @ingroup public */\r
1508 \r
1509 /** @defgroup publicConfig Configuration\r
1510  *  @ingroup public */\r
1511 \r
1512 /** @defgroup publicLang Internationalization\r
1513  *  @ingroup publicConfig */\r
1514 \r
1515 /** @defgroup publicOutput HTML output\r
1516  *  @ingroup publicConfig */\r
1517 \r
1518 /** @defgroup publicPGTStorage PGT storage\r
1519  *  @ingroup publicConfig */\r
1520 \r
1521 /** @defgroup publicDebug Debugging\r
1522  *  @ingroup public */\r
1523 \r
1524 /** @defgroup internal Implementation */\r
1525 \r
1526 /** @defgroup internalAuthentication Authentication\r
1527  *  @ingroup internal */\r
1528 \r
1529 /** @defgroup internalBasic CAS Basic client features (CAS 1.0, Service Tickets)\r
1530  *  @ingroup internal */\r
1531 \r
1532 /** @defgroup internalProxy CAS Proxy features (CAS 2.0, Proxy Granting Tickets)\r
1533  *  @ingroup internal */\r
1534 \r
1535 /** @defgroup internalPGTStorage PGT storage\r
1536  *  @ingroup internalProxy */\r
1537 \r
1538 /** @defgroup internalPGTStorageDB PGT storage in a database\r
1539  *  @ingroup internalPGTStorage */\r
1540 \r
1541 /** @defgroup internalPGTStorageFile PGT storage on the filesystem\r
1542  *  @ingroup internalPGTStorage */\r
1543 \r
1544 /** @defgroup internalCallback Callback from the CAS server\r
1545  *  @ingroup internalProxy */\r
1546 \r
1547 /** @defgroup internalProxied CAS proxied client features (CAS 2.0, Proxy Tickets)\r
1548  *  @ingroup internal */\r
1549 \r
1550 /** @defgroup internalConfig Configuration\r
1551  *  @ingroup internal */\r
1552 \r
1553 /** @defgroup internalOutput HTML output\r
1554  *  @ingroup internalConfig */\r
1555 \r
1556 /** @defgroup internalLang Internationalization\r
1557  *  @ingroup internalConfig\r
1558  *\r
1559  * To add a new language:\r
1560  * - 1. define a new constant PHPCAS_LANG_XXXXXX in CAS/CAS.php\r
1561  * - 2. copy any file from CAS/languages to CAS/languages/XXXXXX.php\r
1562  * - 3. Make the translations\r
1563  */\r
1564 \r
1565 /** @defgroup internalDebug Debugging\r
1566  *  @ingroup internal */\r
1567 \r
1568 /** @defgroup internalMisc Miscellaneous\r
1569  *  @ingroup internal */\r
1570 \r
1571 // ########################################################################\r
1572 //  EXAMPLES\r
1573 \r
1574 /**\r
1575  * @example example_simple.php\r
1576  */\r
1577 /**\r
1578  * @example example_proxy.php\r
1579  */\r
1580 /**\r
1581  * @example example_proxy2.php\r
1582  */\r
1583 /**\r
1584  * @example example_lang.php\r
1585  */\r
1586 /**\r
1587  * @example example_html.php\r
1588  */\r
1589 /**\r
1590  * @example example_file.php\r
1591  */\r
1592 /**\r
1593  * @example example_db.php\r
1594  */\r
1595 /**\r
1596  * @example example_service.php\r
1597  */\r
1598 /**\r
1599  * @example example_session_proxy.php\r
1600  */\r
1601 /**\r
1602  * @example example_session_service.php\r
1603  */\r
1604 /**\r
1605  * @example example_gateway.php\r
1606  */\r
1607 /**\r
1608  * @example example_custom_urls.php\r
1609  */\r
1610 ?>\r