From bf3084b608b8a1036f0b091140350813d54c3d0d Mon Sep 17 00:00:00 2001
From: Andy Wermke <andy@dev.next-step-software.com>
Date: Mon, 08 Apr 2013 08:33:51 -0400
Subject: [PATCH] Merge branch 'master' of https://github.com/roundcube/roundcubemail

---
 program/js/list.js                             |   24 +++++++----
 CHANGELOG                                      |    2 +
 program/steps/mail/compose.inc                 |    8 ++--
 program/steps/mail/func.inc                    |    2 
 program/lib/Roundcube/rcube_message.php        |   15 +++----
 program/steps/mail/show.inc                    |    2 
 program/lib/Roundcube/rcube_message_header.php |    7 +++
 program/lib/Roundcube/html.php                 |   12 +++++
 program/steps/mail/mark.inc                    |   10 ++--
 program/steps/mail/copy.inc                    |    8 ++--
 program/steps/mail/move_del.inc                |    2 +
 11 files changed, 57 insertions(+), 35 deletions(-)

diff --git a/CHANGELOG b/CHANGELOG
index c21743d..a9121fc 100644
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -1,6 +1,8 @@
 CHANGELOG Roundcube Webmail
 ===========================
 
+- Fix handling of invalid characters in message headers and output (#1489032)
+- Fix selecting collapsed rows on select-all (#1489036)
 - Fix possible header duplicates when using additional headers (#1489033)
 - Fix session issues with use_https=true (#1488986)
 - Fix blockquote width in sent mail (#1489031)
diff --git a/program/js/list.js b/program/js/list.js
index 8b4857d..cf62a7c 100644
--- a/program/js/list.js
+++ b/program/js/list.js
@@ -780,10 +780,16 @@
   if (!this.rows[this.shift_start] || !this.selection.length)
     this.shift_start = id;
 
-  var n, from_rowIndex = this.rows[this.shift_start].obj.rowIndex,
-    to_rowIndex = this.rows[id].obj.rowIndex,
-    i = ((from_rowIndex < to_rowIndex)? from_rowIndex : to_rowIndex),
-    j = ((from_rowIndex > to_rowIndex)? from_rowIndex : to_rowIndex);
+  var n, i, j, to_row = this.rows[id],
+    from_rowIndex = this.rows[this.shift_start].obj.rowIndex,
+    to_rowIndex = to_row.obj.rowIndex;
+
+  if (!to_row.expanded && to_row.has_children)
+    if (to_row = this.rows[(this.row_children(id)).pop()])
+      to_rowIndex = to_row.obj.rowIndex;
+
+  i = ((from_rowIndex < to_rowIndex) ? from_rowIndex : to_rowIndex),
+  j = ((from_rowIndex > to_rowIndex) ? from_rowIndex : to_rowIndex);
 
   // iterate through the entire message list
   for (n in this.rows) {
@@ -829,7 +835,7 @@
   for (n in this.rows) {
     if (!filter || this.rows[n][filter] == true) {
       this.last_selected = n;
-      this.highlight_row(n, true);
+      this.highlight_row(n, true, true);
     }
     else {
       $(this.rows[n].obj).removeClass('selected').removeClass('unfocused');
@@ -924,7 +930,7 @@
 /**
  * Highlight/unhighlight a row
  */
-highlight_row: function(id, multiple)
+highlight_row: function(id, multiple, norecur)
 {
   if (!this.rows[id])
     return;
@@ -940,7 +946,7 @@
     if (!this.in_selection(id)) { // select row
       this.selection.push(id);
       $(this.rows[id].obj).addClass('selected');
-      if (!this.rows[id].expanded)
+      if (!norecur && !this.rows[id].expanded)
         this.highlight_children(id, true);
     }
     else { // unselect row
@@ -950,7 +956,7 @@
 
       this.selection = a_pre.concat(a_post);
       $(this.rows[id].obj).removeClass('selected').removeClass('unfocused');
-      if (!this.rows[id].expanded)
+      if (!norecur && !this.rows[id].expanded)
         this.highlight_children(id, false);
     }
   }
@@ -968,7 +974,7 @@
   for (i=0; i<len; i++) {
     selected = this.in_selection(children[i]);
     if ((status && !selected) || (!status && selected))
-      this.highlight_row(children[i], true);
+      this.highlight_row(children[i], true, true);
   }
 },
 
diff --git a/program/lib/Roundcube/html.php b/program/lib/Roundcube/html.php
index 5927203..7b30e60 100644
--- a/program/lib/Roundcube/html.php
+++ b/program/lib/Roundcube/html.php
@@ -35,6 +35,7 @@
     public static $common_attrib = array('id','class','style','title','align');
     public static $containers = array('iframe','div','span','p','h1','h2','h3','form','textarea','table','thead','tbody','tr','th','td','style','script');
 
+
     /**
      * Constructor
      *
@@ -332,7 +333,16 @@
      */
     public static function quote($str)
     {
-        return @htmlspecialchars($str, ENT_COMPAT, RCUBE_CHARSET);
+        static $flags;
+
+        if (!$flags) {
+            $flags = ENT_COMPAT;
+            if (defined('ENT_SUBSTITUTE')) {
+                $flags |= ENT_SUBSTITUTE;
+            }
+        }
+
+        return @htmlspecialchars($str, $flags, RCUBE_CHARSET);
     }
 }
 
diff --git a/program/lib/Roundcube/rcube_message.php b/program/lib/Roundcube/rcube_message.php
index 41a114f..69735fc 100644
--- a/program/lib/Roundcube/rcube_message.php
+++ b/program/lib/Roundcube/rcube_message.php
@@ -85,12 +85,13 @@
 
         $this->headers = $this->storage->get_message($uid);
 
-        if (!$this->headers)
+        if (!$this->headers) {
             return;
+        }
 
         $this->mime = new rcube_mime($this->headers->charset);
 
-        $this->subject = $this->mime->decode_mime_string($this->headers->subject);
+        $this->subject = $this->headers->get('subject');
         list(, $this->sender) = each($this->mime->decode_address_list($this->headers->from, 1));
 
         $this->set_safe((intval($_GET['_safe']) || $_SESSION['safe_messages'][$this->folder.':'.$uid]));
@@ -125,15 +126,11 @@
      */
     public function get_header($name, $raw = false)
     {
-        if (empty($this->headers))
+        if (empty($this->headers)) {
             return null;
+        }
 
-        if ($this->headers->$name)
-            $value = $this->headers->$name;
-        else if ($this->headers->others[$name])
-            $value = $this->headers->others[$name];
-
-        return $raw ? $value : $this->mime->decode_header($value);
+        return $this->headers->get($name, !$raw);
     }
 
 
diff --git a/program/lib/Roundcube/rcube_message_header.php b/program/lib/Roundcube/rcube_message_header.php
index 274ae7f..2c5e2b6 100644
--- a/program/lib/Roundcube/rcube_message_header.php
+++ b/program/lib/Roundcube/rcube_message_header.php
@@ -215,7 +215,12 @@
             $value = $this->others[$name];
         }
 
-        return $decode ? rcube_mime::decode_header($value, $this->charset) : $value;
+        if ($decode) {
+            $value = rcube_mime::decode_header($value, $this->charset);
+            $value = rcube_charset::clean($value);
+        }
+
+        return $value;
     }
 
     /**
diff --git a/program/steps/mail/compose.inc b/program/steps/mail/compose.inc
index 36c6d96..b787ca1 100644
--- a/program/steps/mail/compose.inc
+++ b/program/steps/mail/compose.inc
@@ -220,9 +220,9 @@
     }
   }
   else if ($compose_mode == RCUBE_COMPOSE_DRAFT) {
-    if ($MESSAGE->headers->others['x-draft-info']) {
+    if ($draft_info = $MESSAGE->headers->get('x-draft-info')) {
       // get reply_uid/forward_uid to flag the original message when sending
-      $info = rcmail_draftinfo_decode($MESSAGE->headers->others['x-draft-info']);
+      $info = rcmail_draftinfo_decode($draft_info);
 
       if ($info['type'] == 'reply')
         $COMPOSE['reply_uid'] = $info['uid'];
@@ -239,8 +239,8 @@
       }
     }
 
-    if ($MESSAGE->headers->in_reply_to)
-      $COMPOSE['reply_msgid'] = '<'.$MESSAGE->headers->in_reply_to.'>';
+    if ($in_reply_to = $MESSAGE->headers->get('in-reply-to'))
+      $COMPOSE['reply_msgid'] = '<' . $in_reply_to . '>';
 
     $COMPOSE['references']  = $MESSAGE->headers->references;
   }
diff --git a/program/steps/mail/copy.inc b/program/steps/mail/copy.inc
index a72378b..8766574 100644
--- a/program/steps/mail/copy.inc
+++ b/program/steps/mail/copy.inc
@@ -24,10 +24,10 @@
   return;
 
 // move messages
-if (!empty($_POST['_uid']) && !empty($_POST['_target_mbox'])) {
-    $uids = get_input_value('_uid', RCUBE_INPUT_POST);
+if (!empty($_POST['_uid']) && strlen($_POST['_target_mbox'])) {
+    $uids   = get_input_value('_uid', RCUBE_INPUT_POST);
     $target = get_input_value('_target_mbox', RCUBE_INPUT_POST, true);
-    $mbox = get_input_value('_mbox', RCUBE_INPUT_POST, true);
+    $mbox   = get_input_value('_mbox', RCUBE_INPUT_POST, true);
 
     $copied = $RCMAIL->storage->copy_message($uids, $target, $mbox);
 
@@ -47,7 +47,7 @@
 }
 // unknown action or missing query param
 else {
-    exit;
+    $OUTPUT->show_message('internalerror', 'error');
 }
 
 // send response
diff --git a/program/steps/mail/func.inc b/program/steps/mail/func.inc
index 274c40b..6333cf4 100644
--- a/program/steps/mail/func.inc
+++ b/program/steps/mail/func.inc
@@ -896,7 +896,7 @@
  * return table with message headers
  */
 function rcmail_message_headers($attrib, $headers=null)
-  {
+{
   global $OUTPUT, $MESSAGE, $PRINT_MODE, $RCMAIL;
   static $sa_attrib;
 
diff --git a/program/steps/mail/mark.inc b/program/steps/mail/mark.inc
index c220fc5..dfc892e 100644
--- a/program/steps/mail/mark.inc
+++ b/program/steps/mail/mark.inc
@@ -113,7 +113,7 @@
       $OUTPUT->command('set_rowcount', rcmail_get_messagecount_text($msg_count), $mbox);
 
       if ($threading) {
-	    $count = get_input_value('_count', RCUBE_INPUT_POST);
+        $count = get_input_value('_count', RCUBE_INPUT_POST);
       }
 
       // add new rows from next page (if any)
@@ -125,9 +125,9 @@
       }
     }
   }
-
-  $OUTPUT->send();
+}
+else {
+    $OUTPUT->show_message('internalerror', 'error');
 }
 
-exit;
-
+$OUTPUT->send();
diff --git a/program/steps/mail/move_del.inc b/program/steps/mail/move_del.inc
index 3fc6ac5..e21ba2c 100644
--- a/program/steps/mail/move_del.inc
+++ b/program/steps/mail/move_del.inc
@@ -74,6 +74,8 @@
 }
 // unknown action or missing query param
 else {
+    $OUTPUT->show_message('internalerror', 'error');
+    $OUTPUT->send();
     exit;
 }
 
diff --git a/program/steps/mail/show.inc b/program/steps/mail/show.inc
index 552c180..1947c0f 100644
--- a/program/steps/mail/show.inc
+++ b/program/steps/mail/show.inc
@@ -109,7 +109,7 @@
     $OUTPUT->set_env('skip_deleted', true);
   if ($CONFIG['display_next'])
     $OUTPUT->set_env('display_next', true);
-  if ($MESSAGE->headers->others['list-post'])
+  if ($MESSAGE->headers->get('list-post', false))
     $OUTPUT->set_env('list_post', true);
   if ($CONFIG['forward_attachment'])
     $OUTPUT->set_env('forward_attachment', true);

--
Gitblit v1.9.1