@@ -976,47 +976,54 @@ struct aws_future_http_message *s_s3_prepare_upload_part(struct aws_s3_request *
976976 part_prep -> request = request ;
977977 part_prep -> on_complete = aws_future_http_message_acquire (message_future );
978978 if (request -> parallel ) {
979- printf ("PARALLEL\n" );
980- uint64_t offset = 0 ;
981- size_t request_body_size = s_compute_request_body_size (meta_request , request -> part_number , & offset );
982- request -> request_stream = aws_input_stream_new_from_file (
983- allocator , aws_parallel_input_stream_get_file_path (meta_request -> request_body_parallel_stream ));
984- request -> content_length = request_body_size ;
985- aws_input_stream_seek (request -> request_stream , offset , AWS_SSB_BEGIN );
986- struct aws_s3_auto_ranged_put * auto_ranged_put = meta_request -> impl ;
987-
988- /* BEGIN CRITICAL SECTION */
989- aws_s3_meta_request_lock_synced_data (meta_request );
979+ if (request -> num_times_prepared == 0 ) {
980+ uint64_t offset = 0 ;
981+ size_t request_body_size = s_compute_request_body_size (meta_request , request -> part_number , & offset );
982+ request -> request_stream = aws_input_stream_new_from_parallel (
983+ allocator , meta_request -> request_body_parallel_stream , offset , request_body_size );
984+ request -> content_length = request_body_size ;
985+ struct aws_s3_auto_ranged_put * auto_ranged_put = meta_request -> impl ;
986+
987+ /* BEGIN CRITICAL SECTION */
988+ aws_s3_meta_request_lock_synced_data (meta_request );
990989
991- -- auto_ranged_put -> synced_data .num_parts_pending_read ;
990+ -- auto_ranged_put -> synced_data .num_parts_pending_read ;
992991
993- auto_ranged_put -> synced_data .is_body_stream_at_end = false;
994- if (!request -> is_noop ) {
995- /* The part can finish out of order. Resize array-list to be long enough to hold this part,
996- * filling any intermediate slots with NULL. */
997- aws_array_list_ensure_capacity (& auto_ranged_put -> synced_data .part_list , request -> part_number );
998- while (aws_array_list_length (& auto_ranged_put -> synced_data .part_list ) < request -> part_number ) {
999- struct aws_s3_mpu_part_info * null_part = NULL ;
1000- aws_array_list_push_back (& auto_ranged_put -> synced_data .part_list , & null_part );
992+ auto_ranged_put -> synced_data .is_body_stream_at_end = false;
993+ if (!request -> is_noop ) {
994+ /* The part can finish out of order. Resize array-list to be long enough to hold this part,
995+ * filling any intermediate slots with NULL. */
996+ aws_array_list_ensure_capacity (& auto_ranged_put -> synced_data .part_list , request -> part_number );
997+ while (aws_array_list_length (& auto_ranged_put -> synced_data .part_list ) < request -> part_number ) {
998+ struct aws_s3_mpu_part_info * null_part = NULL ;
999+ aws_array_list_push_back (& auto_ranged_put -> synced_data .part_list , & null_part );
1000+ }
1001+ /* Add part to array-list */
1002+ struct aws_s3_mpu_part_info * part =
1003+ aws_mem_calloc (meta_request -> allocator , 1 , sizeof (struct aws_s3_mpu_part_info ));
1004+ part -> size = request -> request_body .len ;
1005+ aws_array_list_set_at (& auto_ranged_put -> synced_data .part_list , & part , request -> part_number - 1 );
10011006 }
1002- /* Add part to array-list */
1003- struct aws_s3_mpu_part_info * part =
1004- aws_mem_calloc (meta_request -> allocator , 1 , sizeof (struct aws_s3_mpu_part_info ));
1005- part -> size = request -> request_body .len ;
1006- aws_array_list_set_at (& auto_ranged_put -> synced_data .part_list , & part , request -> part_number - 1 );
1007- }
1008- aws_s3_meta_request_unlock_synced_data (meta_request );
1009- /* END CRITICAL SECTION */
1007+ aws_s3_meta_request_unlock_synced_data (meta_request );
1008+ /* END CRITICAL SECTION */
10101009
1011- /* We throttle the number of parts that can be "pending read"
1012- * (e.g. only 1 at a time if reading from async-stream).
1013- * Now that read is complete, poke the client to see if it can give us more work.
1014- *
1015- * Poking now gives measurable speedup (1%) for async streaming,
1016- * vs waiting until all the part-prep steps are complete (still need to sign, etc) */
1017- aws_s3_client_schedule_process_work (meta_request -> client );
1010+ /* We throttle the number of parts that can be "pending read"
1011+ * (e.g. only 1 at a time if reading from async-stream).
1012+ * Now that read is complete, poke the client to see if it can give us more work.
1013+ *
1014+ * Poking now gives measurable speedup (1%) for async streaming,
1015+ * vs waiting until all the part-prep steps are complete (still need to sign, etc) */
1016+ aws_s3_client_schedule_process_work (meta_request -> client );
10181017
1019- s_s3_prepare_upload_part_finish (part_prep , AWS_ERROR_SUCCESS );
1018+ s_s3_prepare_upload_part_finish (part_prep , AWS_ERROR_SUCCESS );
1019+ } else {
1020+ printf ("PARALLEL retry\n" );
1021+ /* Not the first time preparing request (e.g. retry).
1022+ * We can skip over the async steps that read the body stream */
1023+ /* Seek back to beginning of the stream. */
1024+ aws_s3_part_streaming_input_stream_reset (request -> request_stream );
1025+ s_s3_prepare_upload_part_finish (part_prep , AWS_ERROR_SUCCESS );
1026+ }
10201027 } else if (request -> num_times_prepared == 0 ) {
10211028 /* Preparing request for the first time.
10221029 * Next async step: read through the body stream until we've
0 commit comments