seq_runtime/
tcp_test.rs

1//! Minimal May TCP test to verify the library works
2//!
3//! This test uses May's networking directly from Rust to verify
4//! the issue isn't with May itself, but with how we're using it.
5
6#[cfg(test)]
7mod tests {
8    use may::coroutine;
9    use may::net::{TcpListener, TcpStream};
10    use std::io::{Read, Write};
11
12    #[test]
13    fn test_may_tcp_basic() {
14        unsafe {
15            // Initialize May (same as scheduler_init)
16            may::config().set_stack_size(0x20000); // 1MB stack
17
18            // Spawn server coroutine
19            let server = coroutine::spawn(|| {
20                let listener = TcpListener::bind("127.0.0.1:19999").unwrap();
21                let (mut stream, _) = listener.accept().unwrap();
22
23                // Read request
24                let mut buffer = Vec::new();
25                let mut chunk = [0u8; 4096];
26                loop {
27                    match stream.read(&mut chunk) {
28                        Ok(0) => break,
29                        Ok(n) => buffer.extend_from_slice(&chunk[..n]),
30                        Err(ref e) if e.kind() == std::io::ErrorKind::WouldBlock => break,
31                        Err(e) => panic!("Server read failed: {}", e),
32                    }
33                    if buffer.len() >= 4 && &buffer[buffer.len() - 4..] == b"\r\n\r\n" {
34                        break;
35                    }
36                }
37
38                // Write response
39                let response = b"HTTP/1.1 200 OK\r\nContent-Length: 5\r\n\r\nHello";
40                stream.write_all(response).unwrap();
41                stream.flush().unwrap();
42            });
43
44            // Give server time to start
45            std::thread::sleep(std::time::Duration::from_millis(100));
46
47            // Spawn client coroutine
48            let client = coroutine::spawn(|| {
49                let mut stream = TcpStream::connect("127.0.0.1:19999").unwrap();
50
51                // Send request
52                stream.write_all(b"GET / HTTP/1.1\r\n\r\n").unwrap();
53                stream.flush().unwrap();
54
55                // Read response
56                let mut buffer = Vec::new();
57                let mut chunk = [0u8; 4096];
58                loop {
59                    match stream.read(&mut chunk) {
60                        Ok(0) => break,
61                        Ok(n) => buffer.extend_from_slice(&chunk[..n]),
62                        Err(ref e) if e.kind() == std::io::ErrorKind::WouldBlock => break,
63                        Err(e) => panic!("Client read failed: {}", e),
64                    }
65                    if buffer.len() >= 5 {
66                        break;
67                    }
68                }
69
70                let response = String::from_utf8(buffer).unwrap();
71                assert!(response.contains("200 OK"));
72                assert!(response.contains("Hello"));
73            });
74
75            // Wait for both to complete
76            server.join().unwrap();
77            client.join().unwrap();
78        }
79    }
80}