diff --git a/classes/pref/feeds.php b/classes/pref/feeds.php
index f57cc37d6..4a77ed8cf 100644
--- a/classes/pref/feeds.php
+++ b/classes/pref/feeds.php
@@ -528,6 +528,9 @@ class Pref_Feeds extends Handler_Protected {
"SELECT * FROM ttrss_feeds WHERE id = '$feed_id' AND
owner_uid = " . $_SESSION["uid"]);
+ $auth_pass_encrypted = sql_bool_to_bool(db_fetch_result($result, 0,
+ "auth_pass_encrypted"));
+
$title = htmlspecialchars(db_fetch_result($result,
0, "title"));
@@ -613,7 +616,14 @@ class Pref_Feeds extends Handler_Protected {
placeHolder=\"".__("Login")."\"
name=\"auth_login\" value=\"$auth_login\">
";
- $auth_pass = htmlspecialchars(db_fetch_result($result, 0, "auth_pass"));
+ $auth_pass = db_fetch_result($result, 0, "auth_pass");
+
+ if ($auth_pass_encrypted) {
+ require_once "crypt.php";
+ $auth_pass = decrypt_string($auth_pass);
+ }
+
+ $auth_pass = htmlspecialchars($auth_pass);
print "link, $_POST["mark_unread_on_update"]));
+ if (strlen(FEED_CRYPT_KEY) > 0) {
+ require_once "crypt.php";
+ $auth_pass = substr(encrypt_string($auth_pass), 0, 250);
+ $auth_pass_encrypted = 'true';
+ } else {
+ $auth_pass_encrypted = 'false';
+ }
+
if (get_pref($this->link, 'ENABLE_FEED_CATS')) {
if ($cat_id && $cat_id != 0) {
$category_qpart = "cat_id = '$cat_id',";
@@ -958,6 +976,7 @@ class Pref_Feeds extends Handler_Protected {
purge_interval = '$purge_intl',
auth_login = '$auth_login',
auth_pass = '$auth_pass',
+ auth_pass_encrypted = $auth_pass_encrypted,
private = $private,
cache_images = $cache_images,
hide_images = $hide_images,
@@ -1003,7 +1022,8 @@ class Pref_Feeds extends Handler_Protected {
break;
case "auth_pass":
- $qpart = "auth_pass = '$auth_pass'";
+ $qpart = "auth_pass = '$auth_pass' AND
+ auth_pass_encrypted = $auth_pass_encrypted";
break;
case "private":
@@ -1841,12 +1861,20 @@ class Pref_Feeds extends Handler_Protected {
"SELECT id FROM ttrss_feeds
WHERE feed_url = '$feed' AND owner_uid = ".$_SESSION["uid"]);
+ if (strlen(FEED_CRYPT_KEY) > 0) {
+ require_once "crypt.php";
+ $pass = substr(encrypt_string($pass), 0, 250);
+ $auth_pass_encrypted = 'true';
+ } else {
+ $auth_pass_encrypted = 'false';
+ }
+
if (db_num_rows($result) == 0) {
$result = db_query($this->link,
"INSERT INTO ttrss_feeds
- (owner_uid,feed_url,title,cat_id,auth_login,auth_pass,update_method)
+ (owner_uid,feed_url,title,cat_id,auth_login,auth_pass,update_method,auth_pass_encrypted)
VALUES ('".$_SESSION["uid"]."', '$feed',
- '[Unknown]', $cat_qpart, '$login', '$pass', 0)");
+ '[Unknown]', $cat_qpart, '$login', '$pass', 0, $auth_pass_encrypted)");
}
db_query($this->link, "COMMIT");
diff --git a/config.php-dist b/config.php-dist
index eb3339742..fc999354b 100644
--- a/config.php-dist
+++ b/config.php-dist
@@ -24,6 +24,13 @@
// You need to set this option correctly otherwise several features
// including PUSH, bookmarklets and browser integration will not work properly.
+ define('FEED_CRYPT_KEY', '');
+ // Key used for encryption of login/passwords for password-protected feeds
+ // in the database. A string of 24 random characters. If left blank, encryption
+ // is not used. Requires mcrypt functions.
+ // Warning: changing this key will make your stored feed passwords impossible
+ // to decrypt.
+
define('SINGLE_USER_MODE', false);
// Operate in single user mode, disables all functionality related to
// multiple users and authentication. Enabling this assumes you have
diff --git a/include/crypt.php b/include/crypt.php
new file mode 100644
index 000000000..f06483ef1
--- /dev/null
+++ b/include/crypt.php
@@ -0,0 +1,36 @@
+
diff --git a/include/functions.php b/include/functions.php
index f5685b89a..73ed97d08 100644
--- a/include/functions.php
+++ b/include/functions.php
@@ -1614,12 +1614,20 @@
"SELECT id FROM ttrss_feeds
WHERE feed_url = '$url' AND owner_uid = ".$_SESSION["uid"]);
+ if (strlen(FEED_CRYPT_KEY) > 0) {
+ require_once "crypt.php";
+ $auth_pass = substr(encrypt_string($auth_pass), 0, 250);
+ $auth_pass_encrypted = 'true';
+ } else {
+ $auth_pass_encrypted = 'false';
+ }
+
if (db_num_rows($result) == 0) {
$result = db_query($link,
"INSERT INTO ttrss_feeds
- (owner_uid,feed_url,title,cat_id, auth_login,auth_pass,update_method)
+ (owner_uid,feed_url,title,cat_id, auth_login,auth_pass,update_method,auth_pass_encrypted)
VALUES ('".$_SESSION["uid"]."', '$url',
- '[Unknown]', $cat_qpart, '$auth_login', '$auth_pass', 0)");
+ '[Unknown]', $cat_qpart, '$auth_login', '$auth_pass', 0, $auth_pass_encrypted)");
$result = db_query($link,
"SELECT id FROM ttrss_feeds WHERE feed_url = '$url'
diff --git a/include/rssfuncs.php b/include/rssfuncs.php
index 6e3ef4cf1..859c575cc 100644
--- a/include/rssfuncs.php
+++ b/include/rssfuncs.php
@@ -203,7 +203,7 @@
$result = db_query($link, "SELECT id,update_interval,auth_login,
feed_url,auth_pass,cache_images,last_updated,
mark_unread_on_update, owner_uid,
- pubsub_state
+ pubsub_state, auth_pass_encrypted
FROM ttrss_feeds WHERE id = '$feed'");
if (db_num_rows($result) == 0) {
@@ -218,6 +218,8 @@
$mark_unread_on_update = sql_bool_to_bool(db_fetch_result($result,
0, "mark_unread_on_update"));
$pubsub_state = db_fetch_result($result, 0, "pubsub_state");
+ $auth_pass_encrypted = sql_bool_to_bool(db_fetch_result($result,
+ 0, "auth_pass_encrypted"));
db_query($link, "UPDATE ttrss_feeds SET last_update_started = NOW()
WHERE id = '$feed'");
@@ -225,6 +227,11 @@
$auth_login = db_fetch_result($result, 0, "auth_login");
$auth_pass = db_fetch_result($result, 0, "auth_pass");
+ if ($auth_pass_encrypted) {
+ require_once "crypt.php";
+ $auth_pass = decrypt_string($auth_pass);
+ }
+
$cache_images = sql_bool_to_bool(db_fetch_result($result, 0, "cache_images"));
$fetch_url = db_fetch_result($result, 0, "feed_url");
diff --git a/include/sanity_check.php b/include/sanity_check.php
index 69309290e..b4102d234 100644
--- a/include/sanity_check.php
+++ b/include/sanity_check.php
@@ -67,6 +67,14 @@
array_push($errors, "Javascript cache is not writable (chmod -R 777 ".CACHE_DIR."/js)");
}
+ if (strlen(FEED_CRYPT_KEY) != 24) {
+ array_push($errors, "FEED_CRYPT_KEY should be exactly 24 characters in length.");
+ }
+
+ if (strlen(FEED_CRYPT_KEY) != 0 && !function_exists("mcrypt_decrypt")) {
+ array_push($errors, "FEED_CRYPT_KEY requires mcrypt functions which are not found.");
+ }
+
if (GENERATED_CONFIG_CHECK != EXPECTED_CONFIG_VERSION) {
array_push($errors,
"Configuration option checker sanity_config.php is outdated, please recreate it using ./utils/regen_config_checks.sh");
diff --git a/include/sanity_config.php b/include/sanity_config.php
index cb1c1e8ca..0c829981e 100644
--- a/include/sanity_config.php
+++ b/include/sanity_config.php
@@ -1,3 +1,3 @@
-
+$requred_defines = array( 'DB_TYPE', 'DB_HOST', 'DB_USER', 'DB_NAME', 'DB_PASS', 'MYSQL_CHARSET', 'SELF_URL_PATH', 'FEED_CRYPT_KEY', 'SINGLE_USER_MODE', 'SIMPLE_UPDATE_MODE', 'PHP_EXECUTABLE', 'LOCK_DIRECTORY', 'CACHE_DIR', 'ICONS_DIR', 'ICONS_URL', 'AUTH_AUTO_CREATE', 'AUTH_AUTO_LOGIN', 'FORCE_ARTICLE_PURGE', 'PUBSUBHUBBUB_HUB', 'PUBSUBHUBBUB_ENABLED', 'SPHINX_ENABLED', 'SPHINX_INDEX', 'ENABLE_REGISTRATION', 'REG_NOTIFY_ADDRESS', 'REG_MAX_USERS', 'SESSION_COOKIE_LIFETIME', 'SESSION_CHECK_ADDRESS', 'SMTP_FROM_NAME', 'SMTP_FROM_ADDRESS', 'DIGEST_SUBJECT', 'SMTP_HOST', 'SMTP_PORT', 'SMTP_LOGIN', 'SMTP_PASSWORD', 'CHECK_FOR_NEW_VERSION', 'ENABLE_GZIP_OUTPUT', 'PLUGINS', 'CONFIG_VERSION'); ?>
diff --git a/install/index.php b/install/index.php
index 3b6a1f544..1aae5da83 100644
--- a/install/index.php
+++ b/install/index.php
@@ -10,6 +10,25 @@