Created
June 18, 2011 21:01
-
-
Save proger/1033500 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| #include <sys/types.h> | |
| #include <sys/sendfile.h> | |
| #include <sys/socket.h> | |
| #include <arpa/inet.h> | |
| #include <netinet/in.h> | |
| #include <netinet/tcp.h> | |
| #include <errno.h> | |
| #include <unistd.h> | |
| #include <limits.h> | |
| #include <fcntl.h> | |
| #include <assert.h> | |
| #include <string.h> | |
| #include <stdlib.h> | |
| #include <stdio.h> | |
| #define PORT 8080 | |
| int | |
| main(int argc, char **argv) | |
| { | |
| int listen_sock, client, file, sock2; | |
| unsigned short bind_port = PORT; | |
| struct sockaddr_in in_addr, client_addr; | |
| #if 0 | |
| char buf[256]; | |
| #endif | |
| char *filename = "file.out"; | |
| int sockopt = 1; | |
| socklen_t addrlen; | |
| int pipe_file[2], pipe_socket[2]; | |
| listen_sock = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); | |
| assert(listen_sock >= 0); | |
| setsockopt(listen_sock, SOL_SOCKET, SO_REUSEADDR, &sockopt, sizeof(sockopt)); | |
| memset(&in_addr, 0, sizeof(in_addr)); | |
| in_addr.sin_family = AF_INET; | |
| in_addr.sin_port = htons(bind_port); | |
| assert(bind(listen_sock, &in_addr, sizeof(in_addr)) == 0); | |
| assert(listen(listen_sock, 16) == 0); | |
| client = accept(listen_sock, &client_addr, &addrlen); | |
| assert(client >= 0); | |
| sock2 = socket(AF_INET, SOCK_DGRAM, 0); | |
| assert(sock2 >= 0); | |
| client_addr.sin_port = htons(8181); | |
| connect(sock2, &client_addr, addrlen); | |
| int opt; | |
| socklen_t olen = sizeof(opt); | |
| getsockopt(sock2, SOL_SOCKET, SO_SNDLOWAT, &opt, &olen); | |
| printf("lowat: %d\n", opt); | |
| getsockopt(sock2, SOL_SOCKET, SO_SNDBUF, &opt, &olen); | |
| printf("sndbuf: %d\n", opt); | |
| file = open(filename, O_CREAT|O_RDWR, 0664); | |
| if (file == -1) { | |
| perror("open"); | |
| return 1; | |
| } | |
| pipe(pipe_file); | |
| pipe(pipe_socket); | |
| ssize_t len; | |
| int flags = 0; /* SPLICE_F_NONBLOCK */ | |
| len = splice(client, NULL, pipe_file[1], NULL, INT_MAX, flags); | |
| printf("splice client->file pipe: %ld\n", len); | |
| len = tee(pipe_file[0], pipe_socket[1], INT_MAX, flags); | |
| printf("tee file->socket: %ld\n", len); | |
| len = splice(pipe_file[0], NULL, file, NULL, INT_MAX, flags); | |
| printf("splice pipe->file: %ld\n", len); | |
| len = splice(pipe_socket[0], NULL, sock2, NULL, INT_MAX, flags); | |
| printf("splice pipe->socket: %ld\n", len); | |
| #if 0 | |
| char buf[] = "otherdata"; | |
| write(sock2, buf, sizeof(buf) - 1); | |
| #endif | |
| close(pipe_file[0]); | |
| close(pipe_file[1]); | |
| close(pipe_socket[0]); | |
| close(pipe_socket[1]); | |
| close(sock2); | |
| close(file); | |
| close(client); | |
| close(listen_sock); | |
| return 0; | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment