Skip to content

fix: resolve binary file upload errors in non-blocking I/O#55

Merged
jos-felipe merged 1 commit intomainfrom
jos-felipe/fix-binary-file-uploads
Aug 23, 2025
Merged

fix: resolve binary file upload errors in non-blocking I/O#55
jos-felipe merged 1 commit intomainfrom
jos-felipe/fix-binary-file-uploads

Conversation

@jos-felipe
Copy link
Copy Markdown
Owner

Summary

  • Fixes critical binary file upload failures with "Empty reply from server" error
  • Resolves non-blocking I/O handling issues for multi-packet HTTP requests
  • Enhances file upload robustness and security validation

Problem Description

Binary file uploads were failing, particularly for files larger than 4KB that get sent in multiple TCP packets. The server was incorrectly treating temporary data unavailability as connection closure, terminating uploads prematurely.

Affected scenarios:

  • Large binary files (images, executables, archives)
  • Files sent in multiple TCP packets
  • PNG/JPG image uploads
  • Any file content with binary data

Root Cause Analysis

The issue occurred in the non-blocking I/O handling:

  1. First packet: HTTP headers parsed successfully
  2. Subsequent packets: Body data arrives later
  3. Bug: recv() returns 0 (no data available yet)
  4. Incorrect handling: Server treats this as "client closed connection"
  5. Result: Connection terminated → upload fails

Technical Solution

Enhanced Connection State Management

  • Added _connectionError flag to HttpRequest class
  • Added hasConnectionError() method to distinguish between:
    • Actual connection closure (should terminate)
    • Temporary data unavailability (should wait)

Improved Non-blocking I/O Logic

  • Smart handling of recv() == 0 based on current parsing state
  • Keep connections open when expecting more body data
  • Only close connections on real errors or at request boundaries

Additional Improvements

  • Robust multipart parsing: Enhanced boundary extraction with quote handling
  • Secure filename parsing: Path traversal protection and validation
  • Directory validation: Check upload directory exists before file operations
  • Consistent responses: Unified redirect to success page

Files Changed

  • include/HttpRequest.hpp: Added connection error tracking
  • src/http/HttpRequest.cpp: Enhanced I/O handling + upload improvements
  • src/server/Server.cpp: Improved connection management logic

Testing Results

All test scenarios now pass with perfect binary integrity:

Small binary files (< 4KB): Work correctly
Large binary files (10KB+): Handle multi-packet uploads successfully
PNG/image files: Upload with perfect integrity (MD5 verified)
Text files: Maintain backward compatibility
Security: Path traversal protection and directory validation

Test Plan

  • Test small binary file upload (< 4KB)
  • Test large binary file upload (10KB+)
  • Test PNG/image file upload
  • Test text file upload (regression test)
  • Verify MD5 checksums match (no corruption)
  • Test upload directory validation
  • Test filename security validation
  • Verify success page redirect works

Impact

  • High: Fixes critical file upload functionality
  • User Experience: Eliminates upload failures for binary files
  • Compatibility: Maintains backward compatibility for existing functionality
  • Security: Adds additional validation layers

This fix resolves a fundamental issue with binary file uploads while enhancing overall upload security and robustness.

## Problem
Binary file uploads were failing with "Empty reply from server" error,
particularly for files larger than 4KB. The issue affected:
- Large binary files (images, executables, archives)
- Files sent in multiple TCP packets
- Non-text files with binary content

## Root Cause
The server incorrectly handled non-blocking I/O when HTTP request data
arrived in multiple packets:
1. Headers received in first packet → parsed successfully
2. Body data arrives in subsequent packets
3. recv() returns 0 (no data available yet)
4. Server incorrectly treats this as "connection closed"
5. Connection terminated prematurely → upload fails

## Solution
**Enhanced Connection State Management:**
- Added `_connectionError` flag to track real connection issues
- Added `hasConnectionError()` method to distinguish between:
  - Actual connection closure
  - Temporary data unavailability

**Improved Non-blocking I/O Handling:**
- Smart logic for recv() == 0 based on parsing state
- Keep connections open when expecting more body data
- Only close on real errors or at request boundaries

**Additional Improvements:**
- Enhanced multipart boundary parsing robustness
- Better filename extraction with security validation
- Upload directory existence validation
- Consistent redirect to success page

## Testing
✅ Small binary files (< 4KB): Work correctly
✅ Large binary files (10KB+): Now handle multi-packet uploads
✅ PNG/image files: Upload with perfect integrity
✅ Text files: Maintain backward compatibility
✅ MD5 verification: All files preserve binary integrity
@Adedayo-Sanni
Copy link
Copy Markdown
Collaborator

Accepted. Great work on verifying if the connection is complete!

@jos-felipe jos-felipe merged commit f1e6275 into main Aug 23, 2025
4 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants