blob: 1a33e7604d643db14331331dc02a3e3af0c9ef37 [file] [log] [blame]
Matthias Andreas Benkardd1f5b682023-11-18 13:18:30 +01001<?php
2// Start session
3if (session_status() !== PHP_SESSION_ACTIVE) {
4 ini_set("session.cookie_httponly", 1);
5 ini_set('session.gc_maxlifetime', $SESSION_LIFETIME);
6}
7
8if (isset($_SERVER['HTTP_X_FORWARDED_PROTO']) &&
9 strtolower($_SERVER['HTTP_X_FORWARDED_PROTO']) == "https") {
10 if (session_status() !== PHP_SESSION_ACTIVE) {
11 ini_set("session.cookie_secure", 1);
12 }
13 $IS_HTTPS = true;
14}
15elseif (isset($_SERVER['HTTPS'])) {
16 if (session_status() !== PHP_SESSION_ACTIVE) {
17 ini_set("session.cookie_secure", 1);
18 }
19 $IS_HTTPS = true;
20}
21else {
22 $IS_HTTPS = false;
23}
24
25if (session_status() !== PHP_SESSION_ACTIVE) {
26 session_start();
27}
28
29if (!isset($_SESSION['CSRF']['TOKEN'])) {
30 $_SESSION['CSRF']['TOKEN'] = bin2hex(random_bytes(32));
31}
32
33// Set session UA
34if (!isset($_SESSION['SESS_REMOTE_UA'])) {
35 $_SESSION['SESS_REMOTE_UA'] = $_SERVER['HTTP_USER_AGENT'];
36}
37
38// Keep session active
39if (isset($_SESSION['LAST_ACTIVITY']) && (time() - $_SESSION['LAST_ACTIVITY'] > $SESSION_LIFETIME)) {
40 session_unset();
41 session_destroy();
42}
43$_SESSION['LAST_ACTIVITY'] = time();
44
45// API
46if (!empty($_SERVER['HTTP_X_API_KEY'])) {
47 $stmt = $pdo->prepare("SELECT * FROM `api` WHERE `api_key` = :api_key AND `active` = '1';");
48 $stmt->execute(array(
49 ':api_key' => preg_replace('/[^a-zA-Z0-9-]/', '', $_SERVER['HTTP_X_API_KEY'])
50 ));
51 $api_return = $stmt->fetch(PDO::FETCH_ASSOC);
52 if (!empty($api_return['api_key'])) {
53 $skip_ip_check = ($api_return['skip_ip_check'] == 1);
54 $remote = get_remote_ip(false);
55 $allow_from = array_map('trim', preg_split( "/( |,|;|\n)/", $api_return['allow_from']));
56 if ($skip_ip_check === true || ip_acl($remote, $allow_from)) {
57 $_SESSION['mailcow_cc_username'] = 'API';
58 $_SESSION['mailcow_cc_role'] = 'admin';
59 $_SESSION['mailcow_cc_api'] = true;
60 if ($api_return['access'] == 'rw') {
61 $_SESSION['mailcow_cc_api_access'] = 'rw';
62 }
63 else {
64 $_SESSION['mailcow_cc_api_access'] = 'ro';
65 }
66 }
67 else {
68 $redis->publish("F2B_CHANNEL", "mailcow UI: Invalid password for API_USER by " . $_SERVER['REMOTE_ADDR']);
69 error_log("mailcow UI: Invalid password for " . $user . " by " . $_SERVER['REMOTE_ADDR']);
70 http_response_code(401);
71 echo json_encode(array(
72 'type' => 'error',
73 'msg' => 'api access denied for ip ' . $_SERVER['REMOTE_ADDR']
74 ));
75 unset($_POST);
76 exit();
77 }
78 }
79 else {
80 $redis->publish("F2B_CHANNEL", "mailcow UI: Invalid password for API_USER by " . $_SERVER['REMOTE_ADDR']);
81 error_log("mailcow UI: Invalid password for " . $user . " by " . $_SERVER['REMOTE_ADDR']);
82 http_response_code(401);
83 echo json_encode(array(
84 'type' => 'error',
85 'msg' => 'authentication failed'
86 ));
87 unset($_POST);
88 exit();
89 }
90}
91
92// Handle logouts
93if (isset($_POST["logout"])) {
94 if (isset($_SESSION["dual-login"])) {
95 $_SESSION["mailcow_cc_username"] = $_SESSION["dual-login"]["username"];
96 $_SESSION["mailcow_cc_role"] = $_SESSION["dual-login"]["role"];
97 unset($_SESSION["dual-login"]);
98 header("Location: /mailbox");
99 exit();
100 }
101 else {
102 session_regenerate_id(true);
103 session_unset();
104 session_destroy();
105 session_write_close();
106 header("Location: /");
107 }
108}
109
110// Check session
111function session_check() {
112 if (isset($_SESSION['mailcow_cc_api']) && $_SESSION['mailcow_cc_api'] === true) {
113 return true;
114 }
115 if (!isset($_SESSION['SESS_REMOTE_UA']) || ($_SESSION['SESS_REMOTE_UA'] != $_SERVER['HTTP_USER_AGENT'])) {
116 $_SESSION['return'][] = array(
117 'type' => 'warning',
118 'msg' => 'session_ua'
119 );
120 return false;
121 }
122 if (!empty($_POST)) {
123 if ($_SESSION['CSRF']['TOKEN'] != $_POST['csrf_token']) {
124 $_SESSION['return'][] = array(
125 'type' => 'warning',
126 'msg' => 'session_token'
127 );
128 return false;
129 }
130 unset($_POST['csrf_token']);
131 $_SESSION['CSRF']['TOKEN'] = bin2hex(random_bytes(32));
132 $_SESSION['CSRF']['TIME'] = time();
133 }
134 return true;
135}
136
137if (isset($_SESSION['mailcow_cc_role']) && session_check() === false) {
138 $_POST = array();
139 $_FILES = array();
140}