]> scripts.mit.edu Git - autoinstalls/wordpress.git/blobdiff - wp-includes/pluggable.php
Wordpress 4.5.3
[autoinstalls/wordpress.git] / wp-includes / pluggable.php
index e41cbfe585183a51c520d68bb88731f18674165d..65419a88f0cd97f7d116e248cfab47f251486698 100644 (file)
@@ -26,8 +26,14 @@ if ( !function_exists('wp_set_current_user') ) :
 function wp_set_current_user($id, $name = '') {
        global $current_user;
 
-       if ( isset( $current_user ) && ( $current_user instanceof WP_User ) && ( $id == $current_user->ID ) )
+       // If `$id` matches the user who's already current, there's nothing to do.
+       if ( isset( $current_user )
+               && ( $current_user instanceof WP_User )
+               && ( $id == $current_user->ID )
+               && ( null !== $id )
+       ) {
                return $current_user;
+       }
 
        $current_user = new WP_User( $id, $name );
 
@@ -48,81 +54,19 @@ if ( !function_exists('wp_get_current_user') ) :
 /**
  * Retrieve the current user object.
  *
- * @since 2.0.3
- *
- * @global WP_User $current_user
- *
- * @return WP_User Current user WP_User object
- */
-function wp_get_current_user() {
-       global $current_user;
-
-       get_currentuserinfo();
-
-       return $current_user;
-}
-endif;
-
-if ( !function_exists('get_currentuserinfo') ) :
-/**
- * Populate global variables with information about the currently logged in user.
- *
  * Will set the current user, if the current user is not set. The current user
  * will be set to the logged-in person. If no user is logged-in, then it will
  * set the current user to 0, which is invalid and won't have any permissions.
  *
- * @since 0.71
+ * @since 2.0.3
  *
- * @global WP_User $current_user Checks if the current user is set
+ * @see _wp_get_current_user()
+ * @global WP_User $current_user Checks if the current user is set.
  *
- * @return false|void False on XML-RPC Request and invalid auth cookie.
+ * @return WP_User Current WP_User instance.
  */
-function get_currentuserinfo() {
-       global $current_user;
-
-       if ( ! empty( $current_user ) ) {
-               if ( $current_user instanceof WP_User )
-                       return;
-
-               // Upgrade stdClass to WP_User
-               if ( is_object( $current_user ) && isset( $current_user->ID ) ) {
-                       $cur_id = $current_user->ID;
-                       $current_user = null;
-                       wp_set_current_user( $cur_id );
-                       return;
-               }
-
-               // $current_user has a junk value. Force to WP_User with ID 0.
-               $current_user = null;
-               wp_set_current_user( 0 );
-               return false;
-       }
-
-       if ( defined('XMLRPC_REQUEST') && XMLRPC_REQUEST ) {
-               wp_set_current_user( 0 );
-               return false;
-       }
-
-       /**
-        * Filter the current user.
-        *
-        * The default filters use this to determine the current user from the
-        * request's cookies, if available.
-        *
-        * Returning a value of false will effectively short-circuit setting
-        * the current user.
-        *
-        * @since 3.9.0
-        *
-        * @param int|bool $user_id User ID if one has been determined, false otherwise.
-        */
-       $user_id = apply_filters( 'determine_current_user', false );
-       if ( ! $user_id ) {
-               wp_set_current_user( 0 );
-               return false;
-       }
-
-       wp_set_current_user( $user_id );
+function wp_get_current_user() {
+       return _wp_get_current_user();
 }
 endif;
 
@@ -145,8 +89,9 @@ if ( !function_exists('get_user_by') ) :
  * Retrieve user info by a given field
  *
  * @since 2.8.0
+ * @since 4.4.0 Added 'ID' as an alias of 'id' for the `$field` parameter.
  *
- * @param string     $field The field to retrieve the user with. id | slug | email | login
+ * @param string     $field The field to retrieve the user with. id | ID | slug | email | login.
  * @param int|string $value A value for $field. A user ID, slug, email address, or login name.
  * @return WP_User|false WP_User object on success, false on failure.
  */
@@ -169,7 +114,7 @@ if ( !function_exists('cache_users') ) :
  *
  * @since 3.0.0
  *
- * @global wpdb $wpdb
+ * @global wpdb $wpdb WordPress database abstraction object.
  *
  * @param array $user_ids User ID numbers list
  */
@@ -502,7 +447,7 @@ function wp_mail( $to, $subject, $message, $headers = '', $attachments = array()
 
        // Set custom headers
        if ( !empty( $headers ) ) {
-               foreach( (array) $headers as $name => $content ) {
+               foreach ( (array) $headers as $name => $content ) {
                        $phpmailer->AddCustomHeader( sprintf( '%1$s: %2$s', $name, $content ) );
                }
 
@@ -533,6 +478,19 @@ function wp_mail( $to, $subject, $message, $headers = '', $attachments = array()
        try {
                return $phpmailer->Send();
        } catch ( phpmailerException $e ) {
+
+               $mail_error_data = compact( 'to', 'subject', 'message', 'headers', 'attachments' );
+
+               /**
+                * Fires after a phpmailerException is caught.
+                *
+                * @since 4.4.0
+                *
+                * @param WP_Error $error A WP_Error object with the phpmailerException code, message, and an array
+                *                        containing the mail recipient, subject, message, headers, and attachments.
+                */
+               do_action( 'wp_mail_failed', new WP_Error( $e->getCode(), $e->getMessage(), $mail_error_data ) );
+
                return false;
        }
 }
@@ -540,36 +498,40 @@ endif;
 
 if ( !function_exists('wp_authenticate') ) :
 /**
- * Checks a user's login information and logs them in if it checks out.
+ * Authenticate a user, confirming the login credentials are valid.
  *
  * @since 2.5.0
+ * @since 4.5.0 `$username` now accepts an email address.
  *
- * @param string $username User's username
- * @param string $password User's password
- * @return WP_User|WP_Error WP_User object if login successful, otherwise WP_Error object.
+ * @param string $username User's username or email address.
+ * @param string $password User's password.
+ * @return WP_User|WP_Error WP_User object if the credentials are valid,
+ *                          otherwise WP_Error.
  */
 function wp_authenticate($username, $password) {
        $username = sanitize_user($username);
        $password = trim($password);
 
        /**
-        * Filter the user to authenticate.
+        * Filter whether a set of user login credentials are valid.
         *
-        * If a non-null value is passed, the filter will effectively short-circuit
-        * authentication, returning an error instead.
+        * A WP_User object is returned if the credentials authenticate a user.
+        * WP_Error or null otherwise.
         *
         * @since 2.8.0
+        * @since 4.5.0 `$username` now accepts an email address.
         *
-        * @param null|WP_User $user     User to authenticate.
-        * @param string       $username User login.
-        * @param string       $password User password
+        * @param null|WP_User|WP_Error $user     WP_User if the user is authenticated.
+        *                                        WP_Error or null otherwise.
+        * @param string                $username Username or email address.
+        * @param string                $password User password
         */
        $user = apply_filters( 'authenticate', null, $username, $password );
 
        if ( $user == null ) {
                // TODO what should the error message be? (Or would these even happen?)
                // Only needed if all authentication handlers fail to return anything.
-               $user = new WP_Error('authentication_failed', __('<strong>ERROR</strong>: Invalid username or incorrect password.'));
+               $user = new WP_Error( 'authentication_failed', __( '<strong>ERROR</strong>: Invalid username, email address or incorrect password.' ) );
        }
 
        $ignore_codes = array('empty_username', 'empty_password');
@@ -579,8 +541,9 @@ function wp_authenticate($username, $password) {
                 * Fires after a user login has failed.
                 *
                 * @since 2.5.0
+                * @since 4.5.0 The value of `$username` can now be an email address.
                 *
-                * @param string $username User login.
+                * @param string $username Username or email address.
                 */
                do_action( 'wp_login_failed', $username );
        }
@@ -821,7 +784,7 @@ endif;
 
 if ( !function_exists('wp_set_auth_cookie') ) :
 /**
- * Sets the authentication cookies based on user ID.
+ * Log in a user by setting authentication cookies.
  *
  * The $remember parameter increases the time that the cookie will be kept. The
  * default the cookie is kept without remembering is two days. When $remember is
@@ -864,7 +827,7 @@ function wp_set_auth_cookie( $user_id, $remember = false, $secure = '', $token =
                $secure = is_ssl();
        }
 
-       // Frontend cookie is secure when the auth cookie is secure and the site's home URL is forced HTTPS.
+       // Front-end cookie is secure when the auth cookie is secure and the site's home URL is forced HTTPS.
        $secure_logged_in_cookie = $secure && 'https' === parse_url( get_option( 'home' ), PHP_URL_SCHEME );
 
        /**
@@ -1021,18 +984,14 @@ function auth_redirect() {
                }
        }
 
-       if ( is_user_admin() ) {
-               $scheme = 'logged_in';
-       } else {
-               /**
-                * Filter the authentication redirect scheme.
-                *
-                * @since 2.9.0
-                *
-                * @param string $scheme Authentication redirect scheme. Default empty.
-                */
-               $scheme = apply_filters( 'auth_redirect_scheme', '' );
-       }
+       /**
+        * Filters the authentication redirect scheme.
+        *
+        * @since 2.9.0
+        *
+        * @param string $scheme Authentication redirect scheme. Default empty.
+        */
+       $scheme = apply_filters( 'auth_redirect_scheme', '' );
 
        if ( $user_id = wp_validate_auth_cookie( '',  $scheme) ) {
                /**
@@ -1139,13 +1098,6 @@ function check_ajax_referer( $action = -1, $query_arg = false, $die = true ) {
 
        $result = wp_verify_nonce( $nonce, $action );
 
-       if ( $die && false === $result ) {
-               if ( defined( 'DOING_AJAX' ) && DOING_AJAX )
-                       wp_die( -1 );
-               else
-                       die( '-1' );
-       }
-
        /**
         * Fires once the AJAX request has been validated or not.
         *
@@ -1157,6 +1109,14 @@ function check_ajax_referer( $action = -1, $query_arg = false, $die = true ) {
         */
        do_action( 'check_ajax_referer', $action, $result );
 
+       if ( $die && false === $result ) {
+               if ( defined( 'DOING_AJAX' ) && DOING_AJAX ) {
+                       wp_die( -1 );
+               } else {
+                       die( '-1' );
+               }
+       }
+
        return $result;
 }
 endif;
@@ -1216,7 +1176,8 @@ if ( !function_exists('wp_sanitize_redirect') ) :
  *
  * @since 2.3.0
  *
- * @return string redirect-sanitized URL
+ * @param string $location The path to redirect to.
+ * @return string Redirect-sanitized URL.
  **/
 function wp_sanitize_redirect($location) {
        $regex = '/
@@ -1232,7 +1193,7 @@ function wp_sanitize_redirect($location) {
                ){1,40}                              # ...one or more times
                )/x';
        $location = preg_replace_callback( $regex, '_wp_sanitize_utf8_in_redirect', $location );
-       $location = preg_replace('|[^a-z0-9-~+_.?#=&;,/:%!*\[\]()]|i', '', $location);
+       $location = preg_replace('|[^a-z0-9-~+_.?#=&;,/:%!*\[\]()@]|i', '', $location);
        $location = wp_kses_no_null($location);
 
        // remove %0d and %0a from location
@@ -1248,6 +1209,9 @@ function wp_sanitize_redirect($location) {
  * @access private
  *
  * @see wp_sanitize_redirect()
+ *
+ * @param array $matches RegEx matches against the redirect location.
+ * @return string URL-encoded version of the first RegEx match.
  */
 function _wp_sanitize_utf8_in_redirect( $matches ) {
        return urlencode( $matches[0] );
@@ -1267,6 +1231,9 @@ if ( !function_exists('wp_safe_redirect') ) :
  * but only used in a few places.
  *
  * @since 2.3.0
+ *
+ * @param string $location The path to redirect to.
+ * @param int    $status   Status code to use.
  */
 function wp_safe_redirect($location, $status = 302) {
 
@@ -1312,7 +1279,8 @@ function wp_validate_redirect($location, $default = '') {
        // In php 5 parse_url may fail if the URL query part contains http://, bug #38143
        $test = ( $cut = strpos($location, '?') ) ? substr( $location, 0, $cut ) : $location;
 
-       $lp  = parse_url($test);
+       // @-operator is used to prevent possible warnings in PHP < 5.3.3.
+       $lp = @parse_url($test);
 
        // Give up if malformed URL
        if ( false === $lp )
@@ -1322,9 +1290,17 @@ function wp_validate_redirect($location, $default = '') {
        if ( isset($lp['scheme']) && !('http' == $lp['scheme'] || 'https' == $lp['scheme']) )
                return $default;
 
-       // Reject if scheme is set but host is not. This catches urls like https:host.com for which parse_url does not set the host field.
-       if ( isset($lp['scheme'])  && !isset($lp['host']) )
+       // Reject if certain components are set but host is not. This catches urls like https:host.com for which parse_url does not set the host field.
+       if ( ! isset( $lp['host'] ) && ( isset( $lp['scheme'] ) || isset( $lp['user'] ) || isset( $lp['pass'] ) || isset( $lp['port'] ) ) ) {
                return $default;
+       }
+
+       // Reject malformed components parse_url() can return on odd inputs.
+       foreach ( array( 'user', 'pass', 'host' ) as $component ) {
+               if ( isset( $lp[ $component ] ) && strpbrk( $lp[ $component ], ':/?#@' ) ) {
+                       return $default;
+               }
+       }
 
        $wpp = parse_url(home_url());
 
@@ -1351,8 +1327,8 @@ if ( ! function_exists('wp_notify_postauthor') ) :
  *
  * @since 1.0.0
  *
- * @param int    $comment_id Comment ID
- * @param string $deprecated Not used
+ * @param int|WP_Comment  $comment_id Comment ID or WP_Comment object.
+ * @param string          $deprecated Not used
  * @return bool True on completion. False if no email addresses were specified.
  */
 function wp_notify_postauthor( $comment_id, $deprecated = null ) {
@@ -1361,7 +1337,7 @@ function wp_notify_postauthor( $comment_id, $deprecated = null ) {
        }
 
        $comment = get_comment( $comment_id );
-       if ( empty( $comment ) )
+       if ( empty( $comment ) || empty( $comment->comment_post_ID ) )
                return false;
 
        $post    = get_post( $comment->comment_post_ID );
@@ -1384,7 +1360,7 @@ function wp_notify_postauthor( $comment_id, $deprecated = null ) {
         * @param array $emails     An array of email addresses to receive a comment notification.
         * @param int   $comment_id The comment ID.
         */
-       $emails = apply_filters( 'comment_notification_recipients', $emails, $comment_id );
+       $emails = apply_filters( 'comment_notification_recipients', $emails, $comment->comment_ID );
        $emails = array_filter( $emails );
 
        // If there are no addresses to send the comment to, bail.
@@ -1407,7 +1383,7 @@ function wp_notify_postauthor( $comment_id, $deprecated = null ) {
         *                         Default false.
         * @param int  $comment_id The comment ID.
         */
-       $notify_author = apply_filters( 'comment_notification_notify_author', false, $comment_id );
+       $notify_author = apply_filters( 'comment_notification_notify_author', false, $comment->comment_ID );
 
        // The comment was left by the author
        if ( $author && ! $notify_author && $comment->user_id == $post->post_author ) {
@@ -1436,6 +1412,7 @@ function wp_notify_postauthor( $comment_id, $deprecated = null ) {
        // The blogname option is escaped with esc_html on the way into the database in sanitize_option
        // we want to reverse this for the plain text arena of emails.
        $blogname = wp_specialchars_decode(get_option('blogname'), ENT_QUOTES);
+       $comment_content = wp_specialchars_decode( $comment->comment_content );
 
        switch ( $comment->comment_type ) {
                case 'trackback':
@@ -1443,7 +1420,7 @@ function wp_notify_postauthor( $comment_id, $deprecated = null ) {
                        /* translators: 1: website name, 2: website IP, 3: website hostname */
                        $notify_message .= sprintf( __('Website: %1$s (IP: %2$s, %3$s)'), $comment->comment_author, $comment->comment_author_IP, $comment_author_domain ) . "\r\n";
                        $notify_message .= sprintf( __( 'URL: %s' ), $comment->comment_author_url ) . "\r\n";
-                       $notify_message .= sprintf( __( 'Comment: %s' ), "\r\n" . $comment->comment_content ) . "\r\n\r\n";
+                       $notify_message .= sprintf( __( 'Comment: %s' ), "\r\n" . $comment_content ) . "\r\n\r\n";
                        $notify_message .= __( 'You can see all trackbacks on this post here:' ) . "\r\n";
                        /* translators: 1: blog name, 2: post title */
                        $subject = sprintf( __('[%1$s] Trackback: "%2$s"'), $blogname, $post->post_title );
@@ -1453,7 +1430,7 @@ function wp_notify_postauthor( $comment_id, $deprecated = null ) {
                        /* translators: 1: website name, 2: website IP, 3: website hostname */
                        $notify_message .= sprintf( __('Website: %1$s (IP: %2$s, %3$s)'), $comment->comment_author, $comment->comment_author_IP, $comment_author_domain ) . "\r\n";
                        $notify_message .= sprintf( __( 'URL: %s' ), $comment->comment_author_url ) . "\r\n";
-                       $notify_message .= sprintf( __( 'Comment: %s' ), "\r\n" . $comment->comment_content ) . "\r\n\r\n";
+                       $notify_message .= sprintf( __( 'Comment: %s' ), "\r\n" . $comment_content ) . "\r\n\r\n";
                        $notify_message .= __( 'You can see all pingbacks on this post here:' ) . "\r\n";
                        /* translators: 1: blog name, 2: post title */
                        $subject = sprintf( __('[%1$s] Pingback: "%2$s"'), $blogname, $post->post_title );
@@ -1462,23 +1439,24 @@ function wp_notify_postauthor( $comment_id, $deprecated = null ) {
                        $notify_message  = sprintf( __( 'New comment on your post "%s"' ), $post->post_title ) . "\r\n";
                        /* translators: 1: comment author, 2: author IP, 3: author domain */
                        $notify_message .= sprintf( __( 'Author: %1$s (IP: %2$s, %3$s)' ), $comment->comment_author, $comment->comment_author_IP, $comment_author_domain ) . "\r\n";
-                       $notify_message .= sprintf( __( 'E-mail: %s' ), $comment->comment_author_email ) . "\r\n";
+                       $notify_message .= sprintf( __( 'Email: %s' ), $comment->comment_author_email ) . "\r\n";
                        $notify_message .= sprintf( __( 'URL: %s' ), $comment->comment_author_url ) . "\r\n";
-                       $notify_message .= sprintf( __('Comment: %s' ), "\r\n" . $comment->comment_content ) . "\r\n\r\n";
+                       $notify_message .= sprintf( __('Comment: %s' ), "\r\n" . $comment_content ) . "\r\n\r\n";
                        $notify_message .= __( 'You can see all comments on this post here:' ) . "\r\n";
                        /* translators: 1: blog name, 2: post title */
                        $subject = sprintf( __('[%1$s] Comment: "%2$s"'), $blogname, $post->post_title );
                        break;
        }
        $notify_message .= get_permalink($comment->comment_post_ID) . "#comments\r\n\r\n";
-       $notify_message .= sprintf( __('Permalink: %s'), get_comment_link( $comment_id ) ) . "\r\n";
+       $notify_message .= sprintf( __('Permalink: %s'), get_comment_link( $comment ) ) . "\r\n";
 
-       if ( user_can( $post->post_author, 'edit_comment', $comment_id ) ) {
-               if ( EMPTY_TRASH_DAYS )
-                       $notify_message .= sprintf( __('Trash it: %s'), admin_url("comment.php?action=trash&c=$comment_id") ) . "\r\n";
-               else
-                       $notify_message .= sprintf( __('Delete it: %s'), admin_url("comment.php?action=delete&c=$comment_id") ) . "\r\n";
-               $notify_message .= sprintf( __('Spam it: %s'), admin_url("comment.php?action=spam&c=$comment_id") ) . "\r\n";
+       if ( user_can( $post->post_author, 'edit_comment', $comment->comment_ID ) ) {
+               if ( EMPTY_TRASH_DAYS ) {
+                       $notify_message .= sprintf( __( 'Trash it: %s' ), admin_url( "comment.php?action=trash&c={$comment->comment_ID}#wpbody-content" ) ) . "\r\n";
+               } else {
+                       $notify_message .= sprintf( __( 'Delete it: %s' ), admin_url( "comment.php?action=delete&c={$comment->comment_ID}#wpbody-content" ) ) . "\r\n";
+               }
+               $notify_message .= sprintf( __( 'Spam it: %s' ), admin_url( "comment.php?action=spam&c={$comment->comment_ID}#wpbody-content" ) ) . "\r\n";
        }
 
        $wp_email = 'wordpress@' . preg_replace('#^www\.#', '', strtolower($_SERVER['SERVER_NAME']));
@@ -1507,7 +1485,7 @@ function wp_notify_postauthor( $comment_id, $deprecated = null ) {
         * @param string $notify_message The comment notification email text.
         * @param int    $comment_id     Comment ID.
         */
-       $notify_message = apply_filters( 'comment_notification_text', $notify_message, $comment_id );
+       $notify_message = apply_filters( 'comment_notification_text', $notify_message, $comment->comment_ID );
 
        /**
         * Filter the comment notification email subject.
@@ -1517,7 +1495,7 @@ function wp_notify_postauthor( $comment_id, $deprecated = null ) {
         * @param string $subject    The comment notification email subject.
         * @param int    $comment_id Comment ID.
         */
-       $subject = apply_filters( 'comment_notification_subject', $subject, $comment_id );
+       $subject = apply_filters( 'comment_notification_subject', $subject, $comment->comment_ID );
 
        /**
         * Filter the comment notification email headers.
@@ -1527,7 +1505,7 @@ function wp_notify_postauthor( $comment_id, $deprecated = null ) {
         * @param string $message_headers Headers for the comment notification email.
         * @param int    $comment_id      Comment ID.
         */
-       $message_headers = apply_filters( 'comment_notification_headers', $message_headers, $comment_id );
+       $message_headers = apply_filters( 'comment_notification_headers', $message_headers, $comment->comment_ID );
 
        foreach ( $emails as $email ) {
                @wp_mail( $email, wp_specialchars_decode( $subject ), $notify_message, $message_headers );
@@ -1539,20 +1517,36 @@ endif;
 
 if ( !function_exists('wp_notify_moderator') ) :
 /**
- * Notifies the moderator of the blog about a new comment that is awaiting approval.
+ * Notifies the moderator of the site about a new comment that is awaiting approval.
  *
  * @since 1.0.0
  *
  * @global wpdb $wpdb WordPress database abstraction object.
  *
- * @param int $comment_id Comment ID
- * @return true Always returns true
+ * Uses the {@see 'notify_moderator'} filter to determine whether the site moderator
+ * should be notified, overriding the site setting.
+ *
+ * @param int $comment_id Comment ID.
+ * @return true Always returns true.
  */
 function wp_notify_moderator($comment_id) {
        global $wpdb;
 
-       if ( 0 == get_option( 'moderation_notify' ) )
+       $maybe_notify = get_option( 'moderation_notify' );
+
+       /**
+        * Filter whether to send the site moderator email notifications, overriding the site setting.
+        *
+        * @since 4.4.0
+        *
+        * @param bool $maybe_notify Whether to notify blog moderator.
+        * @param int  $comment_ID   The id of the comment for the notification.
+        */
+       $maybe_notify = apply_filters( 'notify_moderator', $maybe_notify, $comment_id );
+
+       if ( ! $maybe_notify ) {
                return true;
+       }
 
        $comment = get_comment($comment_id);
        $post = get_post($comment->comment_post_ID);
@@ -1570,6 +1564,7 @@ function wp_notify_moderator($comment_id) {
        // The blogname option is escaped with esc_html on the way into the database in sanitize_option
        // we want to reverse this for the plain text arena of emails.
        $blogname = wp_specialchars_decode(get_option('blogname'), ENT_QUOTES);
+       $comment_content = wp_specialchars_decode( $comment->comment_content );
 
        switch ( $comment->comment_type ) {
                case 'trackback':
@@ -1578,7 +1573,7 @@ function wp_notify_moderator($comment_id) {
                        /* translators: 1: website name, 2: website IP, 3: website hostname */
                        $notify_message .= sprintf( __( 'Website: %1$s (IP: %2$s, %3$s)' ), $comment->comment_author, $comment->comment_author_IP, $comment_author_domain ) . "\r\n";
                        $notify_message .= sprintf( __( 'URL: %s' ), $comment->comment_author_url ) . "\r\n";
-                       $notify_message .= __('Trackback excerpt: ') . "\r\n" . $comment->comment_content . "\r\n\r\n";
+                       $notify_message .= __('Trackback excerpt: ') . "\r\n" . $comment_content . "\r\n\r\n";
                        break;
                case 'pingback':
                        $notify_message  = sprintf( __('A new pingback on the post "%s" is waiting for your approval'), $post->post_title ) . "\r\n";
@@ -1586,28 +1581,30 @@ function wp_notify_moderator($comment_id) {
                        /* translators: 1: website name, 2: website IP, 3: website hostname */
                        $notify_message .= sprintf( __( 'Website: %1$s (IP: %2$s, %3$s)' ), $comment->comment_author, $comment->comment_author_IP, $comment_author_domain ) . "\r\n";
                        $notify_message .= sprintf( __( 'URL: %s' ), $comment->comment_author_url ) . "\r\n";
-                       $notify_message .= __('Pingback excerpt: ') . "\r\n" . $comment->comment_content . "\r\n\r\n";
+                       $notify_message .= __('Pingback excerpt: ') . "\r\n" . $comment_content . "\r\n\r\n";
                        break;
                default: // Comments
                        $notify_message  = sprintf( __('A new comment on the post "%s" is waiting for your approval'), $post->post_title ) . "\r\n";
                        $notify_message .= get_permalink($comment->comment_post_ID) . "\r\n\r\n";
                        $notify_message .= sprintf( __( 'Author: %1$s (IP: %2$s, %3$s)' ), $comment->comment_author, $comment->comment_author_IP, $comment_author_domain ) . "\r\n";
-                       $notify_message .= sprintf( __( 'E-mail: %s' ), $comment->comment_author_email ) . "\r\n";
+                       $notify_message .= sprintf( __( 'Email: %s' ), $comment->comment_author_email ) . "\r\n";
                        $notify_message .= sprintf( __( 'URL: %s' ), $comment->comment_author_url ) . "\r\n";
-                       $notify_message .= sprintf( __( 'Comment: %s' ), "\r\n" . $comment->comment_content ) . "\r\n\r\n";
+                       $notify_message .= sprintf( __( 'Comment: %s' ), "\r\n" . $comment_content ) . "\r\n\r\n";
                        break;
        }
 
-       $notify_message .= sprintf( __('Approve it: %s'),  admin_url("comment.php?action=approve&c=$comment_id") ) . "\r\n";
+       $notify_message .= sprintf( __( 'Approve it: %s' ), admin_url( "comment.php?action=approve&c={$comment_id}#wpbody-content" ) ) . "\r\n";
+
        if ( EMPTY_TRASH_DAYS )
-               $notify_message .= sprintf( __('Trash it: %s'), admin_url("comment.php?action=trash&c=$comment_id") ) . "\r\n";
+               $notify_message .= sprintf( __( 'Trash it: %s' ), admin_url( "comment.php?action=trash&c={$comment_id}#wpbody-content" ) ) . "\r\n";
        else
-               $notify_message .= sprintf( __('Delete it: %s'), admin_url("comment.php?action=delete&c=$comment_id") ) . "\r\n";
-       $notify_message .= sprintf( __('Spam it: %s'), admin_url("comment.php?action=spam&c=$comment_id") ) . "\r\n";
+               $notify_message .= sprintf( __( 'Delete it: %s' ), admin_url( "comment.php?action=delete&c={$comment_id}#wpbody-content" ) ) . "\r\n";
+
+       $notify_message .= sprintf( __( 'Spam it: %s' ), admin_url( "comment.php?action=spam&c={$comment_id}#wpbody-content" ) ) . "\r\n";
 
        $notify_message .= sprintf( _n('Currently %s comment is waiting for approval. Please visit the moderation panel:',
                'Currently %s comments are waiting for approval. Please visit the moderation panel:', $comments_waiting), number_format_i18n($comments_waiting) ) . "\r\n";
-       $notify_message .= admin_url("edit-comments.php?comment_status=moderated") . "\r\n";
+       $notify_message .= admin_url( "edit-comments.php?comment_status=moderated#wpbody-content" ) . "\r\n";
 
        $subject = sprintf( __('[%1$s] Please moderate: "%2$s"'), $blogname, $post->post_title );
        $message_headers = '';
@@ -1666,9 +1663,9 @@ if ( !function_exists('wp_password_change_notification') ) :
  *
  * @since 2.7.0
  *
- * @param object $user User Object
+ * @param WP_User $user User object.
  */
-function wp_password_change_notification(&$user) {
+function wp_password_change_notification( $user ) {
        // send a copy of password change notification to the admin
        // but check to see if it's the admin whose password we're changing, and skip this
        if ( 0 !== strcasecmp( $user->user_email, get_option( 'admin_email' ) ) ) {
@@ -1697,8 +1694,7 @@ if ( !function_exists('wp_new_user_notification') ) :
  * @param int    $user_id    User ID.
  * @param null   $deprecated Not used (argument deprecated).
  * @param string $notify     Optional. Type of notification that should happen. Accepts 'admin' or an empty
- *                           string (admin only), or 'both' (admin and user). The empty string value was kept
- *                           for backward-compatibility purposes with the renamed parameter. Default empty.
+ *                           string (admin only), or 'both' (admin and user). Default empty.
  */
 function wp_new_user_notification( $user_id, $deprecated = null, $notify = '' ) {
        if ( $deprecated !== null ) {
@@ -1714,11 +1710,12 @@ function wp_new_user_notification( $user_id, $deprecated = null, $notify = '' )
 
        $message  = sprintf(__('New user registration on your site %s:'), $blogname) . "\r\n\r\n";
        $message .= sprintf(__('Username: %s'), $user->user_login) . "\r\n\r\n";
-       $message .= sprintf(__('E-mail: %s'), $user->user_email) . "\r\n";
+       $message .= sprintf(__('Email: %s'), $user->user_email) . "\r\n";
 
        @wp_mail(get_option('admin_email'), sprintf(__('[%s] New User Registration'), $blogname), $message);
 
-       if ( 'admin' === $notify || empty( $notify ) ) {
+       // `$deprecated was pre-4.3 `$plaintext_pass`. An empty `$plaintext_pass` didn't sent a user notifcation.
+       if ( 'admin' === $notify || ( empty( $deprecated ) && empty( $notify ) ) ) {
                return;
        }
 
@@ -1820,6 +1817,18 @@ function wp_verify_nonce( $nonce, $action = -1 ) {
                return 2;
        }
 
+       /**
+        * Fires when nonce verification fails.
+        *
+        * @since 4.4.0
+        *
+        * @param string     $nonce  The invalid nonce.
+        * @param string|int $action The nonce action.
+        * @param WP_User    $user   The current user object.
+        * @param string     $token  The user's session token.
+        */
+       do_action( 'wp_verify_nonce_failed', $nonce, $action, $user, $token );
+
        // Invalid nonce
        return false;
 }
@@ -1827,9 +1836,11 @@ endif;
 
 if ( !function_exists('wp_create_nonce') ) :
 /**
- * Creates a cryptographic token tied to a specific action, user, and window of time.
+ * Creates a cryptographic token tied to a specific action, user, user session,
+ * and window of time.
  *
  * @since 2.0.3
+ * @since 4.0.0 Session tokens were integrated with nonce creation
  *
  * @param string|int $action Scalar value to add context to the nonce.
  * @return string The token.
@@ -1962,7 +1973,8 @@ if ( !function_exists('wp_hash') ) :
  *
  * @since 2.0.3
  *
- * @param string $data Plain text to hash
+ * @param string $data   Plain text to hash
+ * @param string $scheme Authentication scheme (auth, secure_auth, logged_in, nonce)
  * @return string Hash of $data
  */
 function wp_hash($data, $scheme = 'auth') {
@@ -2017,8 +2029,9 @@ if ( !function_exists('wp_check_password') ) :
  *     against the $hash + $password
  * @uses PasswordHash::CheckPassword
  *
- * @param string $password Plaintext user's password
- * @param string $hash     Hash of the user's password to check against.
+ * @param string     $password Plaintext user's password
+ * @param string     $hash     Hash of the user's password to check against.
+ * @param string|int $user_id  Optional. User ID.
  * @return bool False, if the $password does not match the hashed password
  */
 function wp_check_password($password, $hash, $user_id = '') {
@@ -2038,10 +2051,10 @@ function wp_check_password($password, $hash, $user_id = '') {
                 *
                 * @since 2.5.0
                 *
-                * @param bool   $check    Whether the passwords match.
-                * @param string $password The plaintext password.
-                * @param string $hash     The hashed password.
-                * @param int    $user_id  User ID.
+                * @param bool       $check    Whether the passwords match.
+                * @param string     $password The plaintext password.
+                * @param string     $hash     The hashed password.
+                * @param string|int $user_id  User ID. Can be empty.
                 */
                return apply_filters( 'check_password', $check, $password, $hash, $user_id );
        }
@@ -2102,9 +2115,11 @@ if ( !function_exists('wp_rand') ) :
  * Generates a random number
  *
  * @since 2.6.2
+ * @since 4.4.0 Uses PHP7 random_int() or the random_compat library if available.
  *
  * @global string $rnd_value
  * @staticvar string $seed
+ * @staticvar bool $external_rand_source_available
  *
  * @param int $min Lower limit for the generated number
  * @param int $max Upper limit for the generated number
@@ -2113,6 +2128,34 @@ if ( !function_exists('wp_rand') ) :
 function wp_rand( $min = 0, $max = 0 ) {
        global $rnd_value;
 
+       // Some misconfigured 32bit environments (Entropy PHP, for example) truncate integers larger than PHP_INT_MAX to PHP_INT_MAX rather than overflowing them to floats.
+       $max_random_number = 3000000000 === 2147483647 ? (float) "4294967295" : 4294967295; // 4294967295 = 0xffffffff
+
+       // We only handle Ints, floats are truncated to their integer value.
+       $min = (int) $min;
+       $max = (int) $max;
+
+       // Use PHP's CSPRNG, or a compatible method
+       static $use_random_int_functionality = true;
+       if ( $use_random_int_functionality ) {
+               try {
+                       $_max = ( 0 != $max ) ? $max : $max_random_number;
+                       // wp_rand() can accept arguments in either order, PHP cannot.
+                       $_max = max( $min, $_max );
+                       $_min = min( $min, $_max );
+                       $val = random_int( $_min, $_max );
+                       if ( false !== $val ) {
+                               return absint( $val );
+                       } else {
+                               $use_random_int_functionality = false;
+                       }
+               } catch ( Error $e ) {
+                       $use_random_int_functionality = false;
+               } catch ( Exception $e ) {
+                       $use_random_int_functionality = false;
+               }
+       }
+
        // Reset $rnd_value after 14 uses
        // 32(md5) + 40(sha1) + 40(sha1) / 8 = 14 random numbers from $rnd_value
        if ( strlen($rnd_value) < 8 ) {
@@ -2137,9 +2180,6 @@ function wp_rand( $min = 0, $max = 0 ) {
 
        $value = abs(hexdec($value));
 
-       // Some misconfigured 32bit environments (Entropy PHP, for example) truncate integers larger than PHP_INT_MAX to PHP_INT_MAX rather than overflowing them to floats.
-       $max_random_number = 3000000000 === 2147483647 ? (float) "4294967295" : 4294967295; // 4294967295 = 0xffffffff
-
        // Reduce the value to be within the min - max range
        if ( $max != 0 )
                $value = $min + ( $max - $min + 1 ) * $value / ( $max_random_number + 1 );
@@ -2184,12 +2224,12 @@ if ( !function_exists( 'get_avatar' ) ) :
  * @since 4.2.0 Optional `$args` parameter added.
  *
  * @param mixed $id_or_email The Gravatar to retrieve. Accepts a user_id, gravatar md5 hash,
- *                           user email, WP_User object, WP_Post object, or comment object.
+ *                           user email, WP_User object, WP_Post object, or WP_Comment object.
  * @param int    $size       Optional. Height and width of the avatar image file in pixels. Default 96.
  * @param string $default    Optional. URL for the default image or a default type. Accepts '404'
  *                           (return a 404 instead of a default image), 'retro' (8bit), 'monsterid'
  *                           (monster), 'wavatar' (cartoon face), 'indenticon' (the "quilt"),
- *                           'mystery', 'mm', or 'mysterman' (The Oyster Man), 'blank' (transparent GIF),
+ *                           'mystery', 'mm', or 'mysteryman' (The Oyster Man), 'blank' (transparent GIF),
  *                           or 'gravatar_default' (the Gravatar logo). Default is the value of the
  *                           'avatar_default' option, with a fallback of 'mystery'.
  * @param string $alt        Optional. Alternative text to use in &lt;img&gt; tag. Default empty.
@@ -2244,17 +2284,22 @@ function get_avatar( $id_or_email, $size = 96, $default = '', $alt = '', $args =
                $args['width'] = $args['size'];
        }
 
+       if ( is_object( $id_or_email ) && isset( $id_or_email->comment_ID ) ) {
+               $id_or_email = get_comment( $id_or_email );
+       }
+
        /**
         * Filter whether to retrieve the avatar URL early.
         *
         * Passing a non-null value will effectively short-circuit get_avatar(), passing
-        * the value through the {@see 'pre_get_avatar'} filter and returning early.
+        * the value through the {@see 'get_avatar'} filter and returning early.
         *
         * @since 4.2.0
         *
-        * @param string            $avatar      HTML for the user's avatar. Default null.
-        * @param int|object|string $id_or_email A user ID, email address, or comment object.
-        * @param array             $args        Arguments passed to get_avatar_url(), after processing.
+        * @param string $avatar      HTML for the user's avatar. Default null.
+        * @param mixed  $id_or_email The Gravatar to retrieve. Accepts a user_id, gravatar md5 hash,
+        *                            user email, WP_User object, WP_Post object, or WP_Comment object.
+        * @param array  $args        Arguments passed to get_avatar_url(), after processing.
         */
        $avatar = apply_filters( 'pre_get_avatar', null, $id_or_email, $args );
 
@@ -2308,12 +2353,13 @@ function get_avatar( $id_or_email, $size = 96, $default = '', $alt = '', $args =
         * @since 2.5.0
         * @since 4.2.0 The `$args` parameter was added.
         *
-        * @param string            $avatar      &lt;img&gt; tag for the user's avatar.
-        * @param int|object|string $id_or_email A user ID, email address, or comment object.
-        * @param int               $size        Square avatar width and height in pixels to retrieve.
-        * @param string            $alt         Alternative text to use in the avatar image tag.
+        * @param string $avatar      &lt;img&gt; tag for the user's avatar.
+        * @param mixed  $id_or_email The Gravatar to retrieve. Accepts a user_id, gravatar md5 hash,
+        *                            user email, WP_User object, WP_Post object, or WP_Comment object.
+        * @param int    $size        Square avatar width and height in pixels to retrieve.
+        * @param string $alt         Alternative text to use in the avatar image tag.
         *                                       Default empty.
-        * @param array             $args        Arguments passed to get_avatar_data(), after processing.
+        * @param array  $args        Arguments passed to get_avatar_data(), after processing.
         */
        return apply_filters( 'get_avatar', $avatar, $id_or_email, $args['size'], $args['default'], $args['alt'], $args );
 }
@@ -2351,7 +2397,7 @@ function wp_text_diff( $left_string, $right_string, $args = null ) {
        $defaults = array( 'title' => '', 'title_left' => '', 'title_right' => '' );
        $args = wp_parse_args( $args, $defaults );
 
-       if ( !class_exists( 'WP_Text_Diff_Renderer_Table' ) )
+       if ( ! class_exists( 'WP_Text_Diff_Renderer_Table', false ) )
                require( ABSPATH . WPINC . '/wp-diff.php' );
 
        $left_string  = normalize_whitespace($left_string);