phpBB 2.0.21 to phpBB 2.0.22 Code Changes

These are the code changes introduced between phpBB 2.0.21 and phpBB 2.0.22. If you have installed many hacks on a forum, but wish to update it, these may help you. It is often easier to apply code changes such as these instead of replacing and rehacking your current files.

These code changes use the following instruction labels:
filename - The name of a file to be edited. Equivalent to an OPEN action in a hack or modification.
FIND - This indicates lines of code you should locate. Changes will be made in reference to this code.
REPLACE WITH - This code should completely replace the code in the preceding FIND instruction.
AFTER, ADD - The code in this instruction should be added on a new line after the last line of code in the preceding FIND instruction.
BEFORE, ADD - The code in this instruction should be added on a new line before the first line of code in the preceding FIND instruction.
FIND AND DELETE - Locate the code in this instruction as with a FIND statement, and then delete the code.
INLINE - This will always precede one of the other labels. An example would be INLINE FIND. INLINE labels work in the same way as the normal labels, with the exception that they operate on a smaller portion of a specific line referenced in the previous FIND instruction. Any new code added in an INLINE instruction should be placed on the same line, instead of on a new line.

Once you have completed the code changes, create an install/ directory in your forum's root directory, and upload the update_to_latest.php file that comes in any phpBB 2.0.22 download to the install/ directory. Run update_to_latest.php by opening it via your web browser, just as you would a normal forum page. Afterward, delete the file and the install/ directory so that your forum is accessible again.

Now, onward to the file changes!

admin/admin_board.php

FIND

Code:
         $new['server_name'] = str_replace('http://', '', $new['server_name']);
      }

AFTER, ADD

Code:
      // Attempt to prevent a mistake with this value.
      if ($config_name == 'avatar_path')
      {
         $new['avatar_path'] = trim($new['avatar_path']);
         if (strstr($new['avatar_path'], "\0") || !is_dir($phpbb_root_path . $new['avatar_path']) || !is_writable($phpbb_root_path . $new['avatar_path']))
         {
            $new['avatar_path'] = $default_config['avatar_path'];
         }
      }

groupcp.php

FIND

Code:
$start = ( isset($HTTP_GET_VARS['start']) ) ? intval($HTTP_GET_VARS['start']) : 0;

AFTER, ADD

Code:
$start = ($start < 0) ? 0 : $start;

FIND

Code:
                     FROM " . AUTH_ACCESS_TABLE . " aa
                     WHERE aa.group_id = g.group_id 
                  )
               )";

REPLACE WITH

Code:
                     FROM " . AUTH_ACCESS_TABLE . " aa
                     WHERE aa.group_id = g.group_id 
                  )
               )
            ORDER BY aa.auth_mod DESC";

FIND

Code:
         $sql = "SELECT g.group_moderator, g.group_type, aa.auth_mod
            FROM " . GROUPS_TABLE . " g, " . AUTH_ACCESS_TABLE . " aa
            WHERE g.group_id = $group_id
               AND aa.group_id (+) = g.group_id";

REPLACE WITH

Code:
         $sql = "SELECT g.group_moderator, g.group_type, aa.auth_mod
            FROM " . GROUPS_TABLE . " g, " . AUTH_ACCESS_TABLE . " aa
            WHERE g.group_id = $group_id
               AND aa.group_id (+) = g.group_id
            ORDER BY aa.auth_mod DESC";

FIND

Code:
         $sql = "SELECT g.group_moderator, g.group_type, aa.auth_mod
            FROM ( " . GROUPS_TABLE . " g
            LEFT JOIN " . AUTH_ACCESS_TABLE . " aa ON aa.group_id = g.group_id )
            WHERE g.group_id = $group_id";

REPLACE WITH

Code:
         $sql = "SELECT g.group_moderator, g.group_type, aa.auth_mod
            FROM ( " . GROUPS_TABLE . " g
            LEFT JOIN " . AUTH_ACCESS_TABLE . " aa ON aa.group_id = g.group_id )
            WHERE g.group_id = $group_id
            ORDER BY aa.auth_mod DESC";

includes/functions.php

FIND

Code:
   if (strstr(urldecode($url), "\n") || strstr(urldecode($url), "\r"))

REPLACE WITH

Code:
   if (strstr(urldecode($url), "\n") || strstr(urldecode($url), "\r") || strstr(urldecode($url), ';url'))

includes/usercp_email.php

FIND

Code:
   $row = $db->sql_fetchrow($result);

REPLACE WITH

Code:
   if ( $row = $db->sql_fetchrow($result) )
   {

Please note that the following FIND/REPLACE WITH pair alters only the amount of spacing before each line. It has no effect on the function of your forum, so you could skip this if you so desire. Doing so may effect the install process of modifications later, however.
FIND

Code:
   $username = $row['username'];
   $user_email = $row['user_email'];
   $user_lang = $row['user_lang'];

   if ( $row['user_viewemail'] || $userdata['user_level'] == ADMIN )
   {
      if ( time() - $userdata['user_emailtime'] < $board_config['flood_interval'] )
      {
         message_die(GENERAL_MESSAGE, $lang['Flood_email_limit']);
      }

      if ( isset($HTTP_POST_VARS['submit']) )
      {
         $error = FALSE;

         if ( !empty($HTTP_POST_VARS['subject']) )
         {
            $subject = trim(stripslashes($HTTP_POST_VARS['subject']));
         }
         else
         {
            $error = TRUE;
            $error_msg = ( !empty($error_msg) ) ? $error_msg . '<br />' . $lang['Empty_subject_email'] : $lang['Empty_subject_email'];
         }

         if ( !empty($HTTP_POST_VARS['message']) )
         {
            $message = trim(stripslashes($HTTP_POST_VARS['message']));
         }
         else
         {
            $error = TRUE;
            $error_msg = ( !empty($error_msg) ) ? $error_msg . '<br />' . $lang['Empty_message_email'] : $lang['Empty_message_email'];
         }

         if ( !$error )
         {
            $sql = "UPDATE " . USERS_TABLE . "
               SET user_emailtime = " . time() . "
               WHERE user_id = " . $userdata['user_id'];
            if ( $result = $db->sql_query($sql) )
            {
               include($phpbb_root_path . 'includes/emailer.'.$phpEx);
               $emailer = new emailer($board_config['smtp_delivery']);

               $emailer->from($userdata['user_email']);
               $emailer->replyto($userdata['user_email']);

               $email_headers = 'X-AntiAbuse: Board servername - ' . $server_name . "\n";
               $email_headers .= 'X-AntiAbuse: User_id - ' . $userdata['user_id'] . "\n";
               $email_headers .= 'X-AntiAbuse: Username - ' . $userdata['username'] . "\n";
               $email_headers .= 'X-AntiAbuse: User IP - ' . decode_ip($user_ip) . "\n";

               $emailer->use_template('profile_send_email', $user_lang);
               $emailer->email_address($user_email);
               $emailer->set_subject($subject);
               $emailer->extra_headers($email_headers);

               $emailer->assign_vars(array(
                  'SITENAME' => $board_config['sitename'],
                  'BOARD_EMAIL' => $board_config['board_email'],
                  'FROM_USERNAME' => $userdata['username'],
                  'TO_USERNAME' => $username,
                  'MESSAGE' => $message)
               );
               $emailer->send();
               $emailer->reset();

               if ( !empty($HTTP_POST_VARS['cc_email']) )
               {
                  $emailer->from($userdata['user_email']);
                  $emailer->replyto($userdata['user_email']);
                  $emailer->use_template('profile_send_email');
                  $emailer->email_address($userdata['user_email']);
                  $emailer->set_subject($subject);

                  $emailer->assign_vars(array(
                     'SITENAME' => $board_config['sitename'],
                     'BOARD_EMAIL' => $board_config['board_email'],
                     'FROM_USERNAME' => $userdata['username'],
                     'TO_USERNAME' => $username,
                     'MESSAGE' => $message)
                  );
                  $emailer->send();
                  $emailer->reset();
               }

               $template->assign_vars(array(
                  'META' => '<meta http-equiv="refresh" content="5;url=' . append_sid("index.$phpEx") . '">')
               );

               $message = $lang['Email_sent'] . '<br /><br />' . sprintf($lang['Click_return_index'],  '<a href="' . append_sid("index.$phpEx") . '">', '</a>');

               message_die(GENERAL_MESSAGE, $message);
            }
            else
            {
               message_die(GENERAL_ERROR, 'Could not update last email time', '', __LINE__, __FILE__, $sql);
            }
         }
      }

      include($phpbb_root_path . 'includes/page_header.'.$phpEx);

      $template->set_filenames(array(
         'body' => 'profile_send_email.tpl')
      );
      make_jumpbox('viewforum.'.$phpEx);

      if ( $error )
      {
         $template->set_filenames(array(
            'reg_header' => 'error_body.tpl')
         );
         $template->assign_vars(array(
            'ERROR_MESSAGE' => $error_msg)
         );
         $template->assign_var_from_handle('ERROR_BOX', 'reg_header');
      }

      $template->assign_vars(array(
         'USERNAME' => $username,

         'S_HIDDEN_FIELDS' => '',
         'S_POST_ACTION' => append_sid("profile.$phpEx?mode=email&amp;" . POST_USERS_URL . "=$user_id"),

         'L_SEND_EMAIL_MSG' => $lang['Send_email_msg'],
         'L_RECIPIENT' => $lang['Recipient'],
         'L_SUBJECT' => $lang['Subject'],
         'L_MESSAGE_BODY' => $lang['Message_body'],
         'L_MESSAGE_BODY_DESC' => $lang['Email_message_desc'],
         'L_EMPTY_SUBJECT_EMAIL' => $lang['Empty_subject_email'],
         'L_EMPTY_MESSAGE_EMAIL' => $lang['Empty_message_email'],
         'L_OPTIONS' => $lang['Options'],
         'L_CC_EMAIL' => $lang['CC_email'],
         'L_SPELLCHECK' => $lang['Spellcheck'],
         'L_SEND_EMAIL' => $lang['Send_email'])
      );

      $template->pparse('body');

      include($phpbb_root_path . 'includes/page_tail.'.$phpEx);
   }
   else
   {
      message_die(GENERAL_MESSAGE, $lang['User_prevent_email']);
   }
}
else
{
   message_die(GENERAL_MESSAGE, $lang['User_not_exist']);
}

REPLACE WITH

Code:
      $username = $row['username'];
      $user_email = $row['user_email'];
      $user_lang = $row['user_lang'];
   
      if ( $row['user_viewemail'] || $userdata['user_level'] == ADMIN )
      {
         if ( time() - $userdata['user_emailtime'] < $board_config['flood_interval'] )
         {
            message_die(GENERAL_MESSAGE, $lang['Flood_email_limit']);
         }
   
         if ( isset($HTTP_POST_VARS['submit']) )
         {
            $error = FALSE;
   
            if ( !empty($HTTP_POST_VARS['subject']) )
            {
               $subject = trim(stripslashes($HTTP_POST_VARS['subject']));
            }
            else
            {
               $error = TRUE;
               $error_msg = ( !empty($error_msg) ) ? $error_msg . '<br />' . $lang['Empty_subject_email'] : $lang['Empty_subject_email'];
            }
   
            if ( !empty($HTTP_POST_VARS['message']) )
            {
               $message = trim(stripslashes($HTTP_POST_VARS['message']));
            }
            else
            {
               $error = TRUE;
               $error_msg = ( !empty($error_msg) ) ? $error_msg . '<br />' . $lang['Empty_message_email'] : $lang['Empty_message_email'];
            }
   
            if ( !$error )
            {
               $sql = "UPDATE " . USERS_TABLE . "
                  SET user_emailtime = " . time() . "
                  WHERE user_id = " . $userdata['user_id'];
               if ( $result = $db->sql_query($sql) )
               {
                  include($phpbb_root_path . 'includes/emailer.'.$phpEx);
                  $emailer = new emailer($board_config['smtp_delivery']);
   
                  $emailer->from($userdata['user_email']);
                  $emailer->replyto($userdata['user_email']);
   
                  $email_headers = 'X-AntiAbuse: Board servername - ' . $server_name . "\n";
                  $email_headers .= 'X-AntiAbuse: User_id - ' . $userdata['user_id'] . "\n";
                  $email_headers .= 'X-AntiAbuse: Username - ' . $userdata['username'] . "\n";
                  $email_headers .= 'X-AntiAbuse: User IP - ' . decode_ip($user_ip) . "\n";
   
                  $emailer->use_template('profile_send_email', $user_lang);
                  $emailer->email_address($user_email);
                  $emailer->set_subject($subject);
                  $emailer->extra_headers($email_headers);
   
                  $emailer->assign_vars(array(
                     'SITENAME' => $board_config['sitename'],
                     'BOARD_EMAIL' => $board_config['board_email'],
                     'FROM_USERNAME' => $userdata['username'],
                     'TO_USERNAME' => $username,
                     'MESSAGE' => $message)
                  );
                  $emailer->send();
                  $emailer->reset();
   
                  if ( !empty($HTTP_POST_VARS['cc_email']) )
                  {
                     $emailer->from($userdata['user_email']);
                     $emailer->replyto($userdata['user_email']);
                     $emailer->use_template('profile_send_email');
                     $emailer->email_address($userdata['user_email']);
                     $emailer->set_subject($subject);
   
                     $emailer->assign_vars(array(
                        'SITENAME' => $board_config['sitename'],
                        'BOARD_EMAIL' => $board_config['board_email'],
                        'FROM_USERNAME' => $userdata['username'],
                        'TO_USERNAME' => $username,
                        'MESSAGE' => $message)
                     );
                     $emailer->send();
                     $emailer->reset();
                  }
   
                  $template->assign_vars(array(
                     'META' => '<meta http-equiv="refresh" content="5;url=' . append_sid("index.$phpEx") . '">')
                  );
   
                  $message = $lang['Email_sent'] . '<br /><br />' . sprintf($lang['Click_return_index'],  '<a href="' . append_sid("index.$phpEx") . '">', '</a>');
   
                  message_die(GENERAL_MESSAGE, $message);
               }
               else
               {
                  message_die(GENERAL_ERROR, 'Could not update last email time', '', __LINE__, __FILE__, $sql);
               }
            }
         }
   
         include($phpbb_root_path . 'includes/page_header.'.$phpEx);
   
         $template->set_filenames(array(
            'body' => 'profile_send_email.tpl')
         );
         make_jumpbox('viewforum.'.$phpEx);
   
         if ( $error )
         {
            $template->set_filenames(array(
               'reg_header' => 'error_body.tpl')
            );
            $template->assign_vars(array(
               'ERROR_MESSAGE' => $error_msg)
            );
            $template->assign_var_from_handle('ERROR_BOX', 'reg_header');
         }
   
         $template->assign_vars(array(
            'USERNAME' => $username,
   
            'S_HIDDEN_FIELDS' => '',
            'S_POST_ACTION' => append_sid("profile.$phpEx?mode=email&amp;" . POST_USERS_URL . "=$user_id"),
   
            'L_SEND_EMAIL_MSG' => $lang['Send_email_msg'],
            'L_RECIPIENT' => $lang['Recipient'],
            'L_SUBJECT' => $lang['Subject'],
            'L_MESSAGE_BODY' => $lang['Message_body'],
            'L_MESSAGE_BODY_DESC' => $lang['Email_message_desc'],
            'L_EMPTY_SUBJECT_EMAIL' => $lang['Empty_subject_email'],
            'L_EMPTY_MESSAGE_EMAIL' => $lang['Empty_message_email'],
            'L_OPTIONS' => $lang['Options'],
            'L_CC_EMAIL' => $lang['CC_email'],
            'L_SPELLCHECK' => $lang['Spellcheck'],
            'L_SEND_EMAIL' => $lang['Send_email'])
         );
   
         $template->pparse('body');
   
         include($phpbb_root_path . 'includes/page_tail.'.$phpEx);
      }
      else
      {
         message_die(GENERAL_MESSAGE, $lang['User_prevent_email']);
      }
   }
   else
   {
      message_die(GENERAL_MESSAGE, $lang['User_not_exist']);
   }

FIND
This is the last line of the file. Delete any space after it.

Code:
?>

BEFORE, ADD

Code:
}
else
{
   message_die(GENERAL_ERROR, 'Could not select user data', '', __LINE__, __FILE__, $sql);
}

includes/usercp_register.php

FIND

Code:
   $popup_pm = ( isset($HTTP_POST_VARS['popup_pm']) ) ? ( ($HTTP_POST_VARS['popup_pm']) ? TRUE : 0 ) : TRUE;

AFTER, ADD

Code:
   $sid = (isset($HTTP_POST_VARS['sid'])) ? $HTTP_POST_VARS['sid'] : 0;

FIND

Code:
   include($phpbb_root_path . 'includes/usercp_avatar.'.$phpEx);

AFTER, ADD

Code:
   // session id check
   if ($sid == '' || $sid != $userdata['session_id'])
   {
      $error = true;
      $error_msg .= ( ( isset($error_msg) ) ? '<br />' : '' ) . $lang['Session_invalid'];
   }

FIND

Code:
            message_die(GENERAL_ERROR, 'Could not obtain confirmation code', __LINE__, __FILE__, $sql);

REPLACE WITH

Code:
            message_die(GENERAL_ERROR, 'Could not obtain confirmation code', '', __LINE__, __FILE__, $sql);

FIND

Code:
                  message_die(GENERAL_ERROR, 'Could not delete confirmation code', __LINE__, __FILE__, $sql);

REPLACE WITH

Code:
                  message_die(GENERAL_ERROR, 'Could not delete confirmation code', '', __LINE__, __FILE__, $sql);

FIND

Code:
   $s_hidden_fields = '<input type="hidden" name="mode" value="' . $mode . '" /><input type="hidden" name="agreed" value="true" /><input type="hidden" name="coppa" value="' . $coppa . '" />';

AFTER, ADD

Code:
   $s_hidden_fields .= '<input type="hidden" name="sid" value="' . $userdata['session_id'] . '" />';

language/lang_english/lang_main.php

FIND

Code:
  //
  // That's all, Folks!
  // -------------------------------------------------

BEFORE, ADD

Code:
$lang['Session_invalid'] = 'Invalid Session. Please resubmit the form.';

login.php

FIND

Code:
            if (strstr(urldecode($redirect), "\n") || strstr(urldecode($redirect), "\r"))

REPLACE WITH

Code:
            if (strstr(urldecode($redirect), "\n") || strstr(urldecode($redirect), "\r") || strstr(urldecode($redirect), ';url'))

FIND

Code:
         if (strstr(urldecode($redirect), "\n") || strstr(urldecode($redirect), "\r"))

REPLACE WITH

Code:
         if (strstr(urldecode($redirect), "\n") || strstr(urldecode($redirect), "\r") || strstr(urldecode($redirect), ';url'))

memberlist.php

FIND

Code:
$start = ( isset($HTTP_GET_VARS['start']) ) ? intval($HTTP_GET_VARS['start']) : 0;

AFTER, ADD

Code:
$start = ($start < 0) ? 0 : $start;

modcp.php

FIND

Code:
$start = ( isset($HTTP_GET_VARS['start']) ) ? intval($HTTP_GET_VARS['start']) : 0;

AFTER, ADD

Code:
$start = ($start < 0) ? 0 : $start;

posting.php

FIND

Code:
$confirm = isset($HTTP_POST_VARS['confirm']) ? true : false;

AFTER, ADD

Code:
$sid = (isset($HTTP_POST_VARS['sid'])) ? $HTTP_POST_VARS['sid'] : 0;

FIND

Code:
      message_die(GENERAL_MESSAGE, $lang['No_valid_mode']);
}

if ( $result = $db->sql_query($sql) )
{
   $post_info = $db->sql_fetchrow($result);
   $db->sql_freeresult($result);

REPLACE WITH

Code:
      message_die(GENERAL_MESSAGE, $lang['No_valid_mode']);
}

if ( ($result = $db->sql_query($sql)) && ($post_info = $db->sql_fetchrow($result)) )
{
   $db->sql_freeresult($result);

FIND

Code:
   $s_hidden_fields .= ( $delete || $mode == "delete" ) ? '<input type="hidden" name="mode" value="delete" />' : '<input type="hidden" name="mode" value="poll_delete" />';

AFTER, ADD

Code:
   $s_hidden_fields .= '<input type="hidden" name="sid" value="' . $userdata['session_id'] . '" />';

FIND

Code:
   $return_message = '';
   $return_meta = '';

AFTER, ADD

Code:

   // session id check
   if ($sid == '' || $sid != $userdata['session_id'])
   {
      $error_msg .= (!empty($error_msg)) ? '<br />' . $lang['Session_invalid'] : $lang['Session_invalid'];
   }

FIND

Code:
      case 'delete':
      case 'poll_delete':

AFTER, ADD

Code:
         if ($error_msg != '')
         {
            message_die(GENERAL_MESSAGE, $error_msg);
         }

FIND

Code:
$hidden_form_fields = '<input type="hidden" name="mode" value="' . $mode . '" />';

AFTER, ADD

Code:
$hidden_form_fields .= '<input type="hidden" name="sid" value="' . $userdata['session_id'] . '" />';

privmsg.php

FIND

Code:
$save = ( isset($HTTP_POST_VARS['save']) ) ? TRUE : 0;

AFTER, ADD

Code:
$sid = (isset($HTTP_POST_VARS['sid'])) ? $HTTP_POST_VARS['sid'] : 0;

FIND

Code:
$start = ( !empty($HTTP_GET_VARS['start']) ) ? intval($HTTP_GET_VARS['start']) : 0;

AFTER, ADD

Code:
$start = ($start < 0) ? 0 : $start;

FIND

Code:
      if ( !empty($HTTP_POST_VARS['username']) )

BEFORE, ADD

Code:
      // session id check
      if ($sid == '' || $sid != $userdata['session_id'])
      {
         $error = true;
         $error_msg .= ( ( !empty($error_msg) ) ? '<br />' : '' ) . $lang['Session_invalid'];
      }

FIND

Code:
      $privmsg_message = preg_replace('#<textarea>#si', '&lt;textarea&gt;', $privmsg_message);

REPLACE WITH

Code:
      // $privmsg_message = preg_replace('#<textarea>#si', '&lt;textarea&gt;', $privmsg_message);

FIND

Code:
         $privmsg_message = preg_replace('#</textarea>#si', '&lt;/textarea&gt;', $privmsg_message);

REPLACE WITH

Code:
         // $privmsg_message = preg_replace('#</textarea>#si', '&lt;/textarea&gt;', $privmsg_message);

FIND

Code:
            $privmsg_message = preg_replace('#</textarea>#si', '&lt;/textarea&gt;', $privmsg_message);

REPLACE WITH

Code:
            // $privmsg_message = preg_replace('#</textarea>#si', '&lt;/textarea&gt;', $privmsg_message);

FIND

Code:
      $template->set_filenames(array(
         'reg_header' => 'error_body.tpl')
      );

BEFORE, ADD

Code:
      $privmsg_message = htmlspecialchars($privmsg_message);

FIND

Code:
   $s_hidden_fields .= '<input type="hidden" name="mode" value="' . $mode . '" />';

AFTER, ADD

Code:
   $s_hidden_fields .= '<input type="hidden" name="sid" value="' . $userdata['session_id'] . '" />';

search.php

FIND

Code:
$start = ( isset($HTTP_GET_VARS['start']) ) ? intval($HTTP_GET_VARS['start']) : 0;

AFTER, ADD

Code:
$start = ($start < 0) ? 0 : $start;

viewforum.php

FIND

Code:
$start = ( isset($HTTP_GET_VARS['start']) ) ? intval($HTTP_GET_VARS['start']) : 0;

AFTER, ADD

Code:
$start = ($start < 0) ? 0 : $start;

viewtopic.php

FIND

Code:
$start = ( isset($HTTP_GET_VARS['start']) ) ? intval($HTTP_GET_VARS['start']) : 0;

AFTER, ADD

Code:
$start = ($start < 0) ? 0 : $start;

templates/subSilver/posting_body.tpl
The changes for this file may not be possible in templates not based on subSilver. If you can't find this line in your file, just skip the change. It is not a vital step.

FIND
Code:
               </select> &nbsp;{L_FONT_SIZE}:<select name="addbbcode20" onChange="bbfontstyle('[size=' + this.form.addbbcode20.options[this.form.addbbcode20.selectedIndex].value + ']', '[/size]')" onMouseOver="helpline('f')">

REPLACE WITH

Code:
               </select> &nbsp;{L_FONT_SIZE}:<select name="addbbcode20" onChange="bbfontstyle('[size=' + this.form.addbbcode20.options[this.form.addbbcode20.selectedIndex].value + ']', '[/size]');this.selectedIndex=0;" onMouseOver="helpline('f')">
                 <option value="0" class="genmed">{L_FONT_SIZE}</option>