Index: wp-includes/theme.php
===================================================================
--- wp-includes/theme.php	(revision 11908)
+++ wp-includes/theme.php	(working copy)
@@ -162,6 +162,18 @@
  * @return array Theme data.
  */
 function get_theme_data( $theme_file ) {
+	$default_headers = array( 
+		'Name' => 'Theme Name', 
+		'URI' => 'Plugin URI', 
+		'Description' => 'Description', 
+		'Author' => 'Author', 
+		'AuthorURI' => 'Author URI',
+		'Version' => 'Version', 
+		'Template' => 'Template', 
+		'Status' => 'Status', 
+		'Tags' => 'Tags'
+		);
+
 	$themes_allowed_tags = array(
 		'a' => array(
 			'href' => array(),'title' => array()
@@ -177,59 +189,42 @@
 		'strong' => array()
 	);
 
-	$theme_data = implode( '', file( $theme_file ) );
-	$theme_data = str_replace ( '\r', '\n', $theme_data );
-	if ( preg_match( '|Theme Name:(.*)$|mi', $theme_data, $theme_name ) )
-		$name = $theme = wp_kses( _cleanup_header_comment($theme_name[1]), $themes_allowed_tags );
-	else
-		$name = $theme = '';
+	$theme_data = get_file_data( $theme_file, $default_headers, 'theme' );
 
-	if ( preg_match( '|Theme URI:(.*)$|mi', $theme_data, $theme_uri ) )
-		$theme_uri = esc_url( _cleanup_header_comment($theme_uri[1]) );
-	else
-		$theme_uri = '';
+	$theme_data['Name'] = $title = wp_kses( $theme_data['Name'], $themes_allowed_tags );
 
-	if ( preg_match( '|Description:(.*)$|mi', $theme_data, $description ) )
-		$description = wptexturize( wp_kses( _cleanup_header_comment($description[1]), $themes_allowed_tags ) );
-	else
-		$description = '';
+	$theme_data['URI'] = esc_url( $theme_data['URI'] );
 
-	if ( preg_match( '|Author URI:(.*)$|mi', $theme_data, $author_uri ) )
-		$author_uri = esc_url( _cleanup_header_comment($author_uri[1]) );
-	else
-		$author_uri = '';
+	$theme_data['Description'] = wptexturize( wp_kses( $theme_data['Description'], $themes_allowed_tags ) );
 
-	if ( preg_match( '|Template:(.*)$|mi', $theme_data, $template ) )
-		$template = wp_kses( _cleanup_header_comment($template[1]), $themes_allowed_tags );
-	else
-		$template = '';
+	$theme_data['AuthorURI'] = esc_url( $theme_data['AuthorURI'] );
 
-	if ( preg_match( '|Version:(.*)|i', $theme_data, $version ) )
-		$version = wp_kses( _cleanup_header_comment($version[1]), $themes_allowed_tags );
-	else
-		$version = '';
+	$theme_data['Template'] = wp_kses( $theme_data['Template'], $themes_allowed_tags );
 
-	if ( preg_match('|Status:(.*)|i', $theme_data, $status) )
-		$status = wp_kses( _cleanup_header_comment($status[1]), $themes_allowed_tags );
+	$theme_data['Version'] = wp_kses( $theme_data['Version'], $themes_allowed_tags );
+
+	if ( $theme_data['Status'] == '' )
+		$theme_data['Status'] = 'publish';
 	else
-		$status = 'publish';
+		$theme_data['Status'] = wp_kses( $theme_data['Status'], $themes_allowed_tags );
 
-	if ( preg_match('|Tags:(.*)|i', $theme_data, $tags) )
-		$tags = array_map( 'trim', explode( ',', wp_kses( _cleanup_header_comment($tags[1]), array() ) ) );
+	if ( $theme_data['Tags'] == '' )
+		$theme_data['Tags'] = array();
 	else
-		$tags = array();
+		$theme_data['Tags'] = array_map( 'trim', explode( ',', wp_kses( $theme_data['Tags'], array() ) ) );
 
-	if ( preg_match( '|Author:(.*)$|mi', $theme_data, $author_name ) ) {
-		if ( empty( $author_uri ) ) {
-			$author = wp_kses( _cleanup_header_comment($author_name[1]), $themes_allowed_tags );
+	if ( $theme_data['Author'] == '' ) {
+		$theme_data['Author'] = __('Anonymous');
+	} else {
+		if ( empty( $theme_data['AuthorURI'] ) ) {
+			$theme_data['Author'] = wp_kses( $theme_data['Author'], $themes_allowed_tags );
 		} else {
-			$author = sprintf( '<a href="%1$s" title="%2$s">%3$s</a>', $author_uri, __( 'Visit author homepage' ), wp_kses( _cleanup_header_comment($author_name[1]), $themes_allowed_tags ) );
+			$author = sprintf( '<a href="%1$s" title="%2$s">%3$s</a>', $theme_data['AuthorURI'], __( 'Visit author homepage' ), wp_kses( $theme_data['Author'], $themes_allowed_tags ) );
 		}
-	} else {
-		$author = __('Anonymous');
 	}
+	unset( $theme_data['AuthorURI'] );
 
-	return array( 'Name' => $name, 'Title' => $theme, 'URI' => $theme_uri, 'Description' => $description, 'Author' => $author, 'Version' => $version, 'Template' => $template, 'Status' => $status, 'Tags' => $tags );
+	return $theme_data;
 }
 
 /**
Index: wp-includes/functions.php
===================================================================
--- wp-includes/functions.php	(revision 11908)
+++ wp-includes/functions.php	(working copy)
@@ -3395,4 +3395,66 @@
 
 	update_option('wp_trash_meta', $trash_meta);
 }
+
+/**
+ * Parse the file contents to retrieve its metadata.
+ *
+ * Searches for metadata for a file, such as a plugin or theme.  Each piece of 
+ * metadata must be on its own line. For a field spanning multple lines, it
+ * must not have any newlines or only parts of it will be displayed.
+ *
+ * Some users have issues with opening large files and manipulating the contents
+ * for want is usually the first 1kiB or 2kiB. This function stops pulling in
+ * the file contents when it has all of the required data.
+ *
+ * The first 8kiB of the file will be pulled in and if the file data is not
+ * within that first 8kiB, then the author should correct their plugin file
+ * and move the data headers to the top.
+ *
+ * The file is assumed to have permissions to allow for scripts to read
+ * the file. This is not checked however and the file is only opened for
+ * reading.
+ *
+ * @since 2.9.0
+ *
+ * @param string $file Path to the file
+ * @param bool $markup If the returned data should have HTML markup applied
+ * @param bool $translate If the returned data should be translated
+ * @return An array of headers
+ */
+function get_file_data( $file, $default_headers, $context = '' ) {
+	// We don't need to write to the file, so just open for reading.
+	$fp = fopen( $file, 'r' );
+
+	// Pull only the first 8kiB of the file in.
+	$file_data = fread( $fp, 8192 );
+
+	// PHP will close file handle, but we are good citizens.
+	fclose( $fp );
+
+	if( $context != '' ) {
+		$extra_headers = apply_filters( "extra_$context".'_headers', array() );
+
+		$extra_headers = array_flip( $extra_headers );
+		foreach( $extra_headers as $key=>$value ) {
+			$extra_headers[$key] = $key;
+		}
+		$all_headers = array_merge($extra_headers, $default_headers);
+	} else {
+		$all_headers = $default_headers;
+	}
+
+	
+	foreach ( $all_headers as $field => $regex ) {
+		preg_match( '/' . preg_quote( $regex, '/' ) . ':(.*)$/mi', $file_data, ${$field});
+		if ( !empty( ${$field} ) )
+			${$field} = _cleanup_header_comment( ${$field}[1] );
+		else
+			${$field} = '';
+	}
+
+	$file_data = compact( array_keys( $all_headers ) );
+	
+	return $file_data;
+}
 ?>
\ No newline at end of file
Index: wp-admin/includes/plugin.php
===================================================================
--- wp-admin/includes/plugin.php	(revision 11908)
+++ wp-admin/includes/plugin.php	(working copy)
@@ -66,38 +66,22 @@
  * @return array See above for description.
  */
 function get_plugin_data( $plugin_file, $markup = true, $translate = true ) {
-	// We don't need to write to the file, so just open for reading.
-	$fp = fopen($plugin_file, 'r');
 
-	// Pull only the first 8kiB of the file in.
-	$plugin_data = fread( $fp, 8192 );
+	$default_headers = array( 
+		'Name' => 'Plugin Name', 
+		'PluginURI' => 'Plugin URI', 
+		'Version' => 'Version', 
+		'Description' => 'Description', 
+		'Author' => 'Author', 
+		'AuthorURI' => 'Author URI', 
+		'TextDomain' => 'Text Domain', 
+		'DomainPath' => 'Domain Path' 
+		);
 
-	// PHP will close file handle, but we are good citizens.
-	fclose($fp);
+	$plugin_data = get_file_data( $plugin_file, $default_headers, 'plugin' );
 
-	preg_match( '|Plugin Name:(.*)$|mi', $plugin_data, $name );
-	preg_match( '|Plugin URI:(.*)$|mi', $plugin_data, $uri );
-	preg_match( '|Version:(.*)|i', $plugin_data, $version );
-	preg_match( '|Description:(.*)$|mi', $plugin_data, $description );
-	preg_match( '|Author:(.*)$|mi', $plugin_data, $author_name );
-	preg_match( '|Author URI:(.*)$|mi', $plugin_data, $author_uri );
-	preg_match( '|Text Domain:(.*)$|mi', $plugin_data, $text_domain );
-	preg_match( '|Domain Path:(.*)$|mi', $plugin_data, $domain_path );
-
-	foreach ( array( 'name', 'uri', 'version', 'description', 'author_name', 'author_uri', 'text_domain', 'domain_path' ) as $field ) {
-		if ( !empty( ${$field} ) )
-			${$field} = _cleanup_header_comment(${$field}[1]);
-		else
-			${$field} = '';
-	}
-
-	$plugin_data = array(
-				'Name' => $name, 'Title' => $name, 'PluginURI' => $uri, 'Description' => $description,
-				'Author' => $author_name, 'AuthorURI' => $author_uri, 'Version' => $version,
-				'TextDomain' => $text_domain, 'DomainPath' => $domain_path
-				);
 	if ( $markup || $translate )
-		$plugin_data = _get_plugin_data_markup_translate($plugin_file, $plugin_data, $markup, $translate);
+		$plugin_data = _get_plugin_data_markup_translate( $plugin_file, $plugin_data, $markup, $translate );
 
 	return $plugin_data;
 }
