Index: wp-includes/js/autosave.dev.js
===================================================================
--- wp-includes/js/autosave.dev.js	(revision 18787)
+++ wp-includes/js/autosave.dev.js	(working copy)
@@ -1,4 +1,4 @@
-var autosave, autosaveLast = '', autosavePeriodical, autosaveOldMessage = '', autosaveDelayPreview = false, notSaved = true, blockSave = false, fullscreen;
+var autosave, autosaveLast = '', autosavePeriodical, autosaveOldMessage = '', autosaveDelayPreview = false, notSaved = true, blockSave = false, fullscreen, autosaveLockRelease = true;
 
 jQuery(document).ready( function($) {
 	var dotabkey = true;
@@ -9,6 +9,7 @@
 	//Disable autosave after the form has been submitted
 	$("#post").submit(function() {
 		$.cancel(autosavePeriodical);
+		autosaveLockRelease = false;
 	});
 
 	$('input[type="submit"], a.submitdelete', '#submitpost').click(function(){
@@ -47,6 +48,22 @@
 		}
 	};
 
+	$(window).unload( function() {
+		if ( ! autosaveLockRelease )
+			return;
+		$.ajax({
+			type: 'POST',
+			url: ajaxurl,
+			async: false,
+			data: {
+				action: 'wp-remove-post-lock',
+				_wpnonce: $('#_wpnonce').val(),
+				post_ID: $('#post_ID').val(),
+				active_post_lock: $('#active_post_lock').val()
+			},
+		});
+	} );
+
 	// preview
 	$('#post-preview').click(function(){
 		if ( $('#auto_draft').val() == '1' && notSaved ) {
@@ -99,9 +116,14 @@
 			sup = res.responses[0].supplemental;
 			if ( 'disable' == sup['disable_autosave'] ) {
 				autosave = function() {};
+				autosaveLockRelease = false;
 				res = { errors: true };
 			}
 
+			if ( sup['active-post-lock'] ) {
+				jQuery('#active_post_lock').val( sup['active-post-lock'] );
+			}
+
 			if ( sup['alert'] ) {
 				jQuery('#autosave-alert').remove();
 				jQuery('#titlediv').after('<div id="autosave-alert" class="error below-h2"><p>' + sup['alert'] + '</p></div>');
Index: wp-admin/admin-ajax.php
===================================================================
--- wp-admin/admin-ajax.php	(revision 18787)
+++ wp-admin/admin-ajax.php	(working copy)
@@ -988,8 +988,10 @@
 			$id = $post->ID;
 	}
 
-	if ( $do_lock && empty( $_POST['auto_draft'] ) && $id && is_numeric( $id ) )
-		wp_set_post_lock( $id );
+	if ( $do_lock && empty( $_POST['auto_draft'] ) && $id && is_numeric( $id ) ) {
+		$lock_result = wp_set_post_lock( $id );
+		$supplemental['active-post-lock'] = implode( ':', $lock_result );
+	}
 
 	if ( $nonce_age == 2 ) {
 		$supplemental['replace-autosavenonce'] = wp_create_nonce('autosave');
@@ -1551,6 +1553,26 @@
 	echo json_encode( array( 'message' => $message, 'last_edited' => $last_edited ) );
 	die();
 	break;
+case 'wp-remove-post-lock' :
+	if ( empty( $_POST['post_ID'] ) || empty( $_POST['active_post_lock'] ) )
+		die( '0' );
+	$post_id = (int) $_POST['post_ID'];
+	if ( ! $post = get_post( $post_id ) )
+		die( '0' );
+
+	check_ajax_referer( 'update-' . $post->post_type . '_' . $post_id );
+
+	if ( ! current_user_can( 'edit_post', $post_id ) )
+		die( '-1' );
+
+	$active_lock = array_map( 'absint', explode( ':', $_POST['active_post_lock'] ) );
+	if ( $active_lock[1] != get_current_user_id() )
+		die( '0' );
+
+	$new_lock = ( time() - apply_filters( 'wp_check_post_lock_window', AUTOSAVE_INTERVAL * 2 ) + 5 ) . ':' . $active_lock[1];
+	update_post_meta( $post_id, '_edit_lock', $new_lock, implode( ':', $active_lock ) );
+	die( '1' );
+
 default :
 	do_action( 'wp_ajax_' . $_POST['action'] );
 	die('0');
Index: wp-admin/includes/post.php
===================================================================
--- wp-admin/includes/post.php	(revision 18790)
+++ wp-admin/includes/post.php	(working copy)
@@ -1227,7 +1227,6 @@
 	$user = isset( $lock[1] ) ? $lock[1] : get_post_meta( $post->ID, '_edit_last', true );
 
 	$time_window = apply_filters( 'wp_check_post_lock_window', AUTOSAVE_INTERVAL * 2 );
-
 	if ( $time && $time > time() - $time_window && $user != get_current_user_id() )
 		return $user;
 	return false;
@@ -1239,7 +1238,8 @@
  * @since 2.5.0
  *
  * @param int $post_id ID of the post to being edited
- * @return bool Returns false if the post doesn't exist of there is no current user
+ * @return bool|array Returns false if the post doesn't exist of there is no current user, or
+ * 	an array of the lock time and the user ID.
  */
 function wp_set_post_lock( $post_id ) {
 	if ( !$post = get_post( $post_id ) )
@@ -1251,6 +1251,7 @@
 	$lock = "$now:$user_id";
 
 	update_post_meta( $post->ID, '_edit_lock', $lock );
+	return array( $now, $user_id );
 }
 
 /**
Index: wp-admin/post.php
===================================================================
--- wp-admin/post.php	(revision 18787)
+++ wp-admin/post.php	(working copy)
@@ -174,7 +174,7 @@
 	if ( $last = wp_check_post_lock( $post->ID ) ) {
 		add_action('admin_notices', '_admin_notice_post_locked' );
 	} else {
-		wp_set_post_lock( $post->ID );
+		$active_post_lock = wp_set_post_lock( $post->ID );
 		wp_enqueue_script('autosave');
 	}
 
Index: wp-admin/edit-form-advanced.php
===================================================================
--- wp-admin/edit-form-advanced.php	(revision 18787)
+++ wp-admin/edit-form-advanced.php	(working copy)
@@ -231,7 +231,10 @@
 <input type="hidden" id="post_type" name="post_type" value="<?php echo esc_attr( $post_type ) ?>" />
 <input type="hidden" id="original_post_status" name="original_post_status" value="<?php echo esc_attr( $post->post_status) ?>" />
 <input type="hidden" id="referredby" name="referredby" value="<?php echo esc_url(stripslashes(wp_get_referer())); ?>" />
+<?php if ( ! empty( $active_post_lock ) ) { ?>
+<input type="hidden" id="active_post_lock" value="<?php echo esc_attr( implode( ':', $active_post_lock ) ); ?>" />
 <?php
+}
 if ( 'draft' != $post->post_status )
 	wp_original_referer_field(true, 'previous');
 
