Merge remote branch 'mplayer/master'
[mplayer/glamo.git] / stream / stream_netstream.h
blob43d42a0a328acbeb7aba77768030d17b3691787d
2 /*
3 * Common stuff for netstream
4 * Packets and so on are defined here along with a few helpers
5 * wich are used by both the client and the server
7 * Data is always low endian
8 */
10 #ifndef MPLAYER_NETSTREAM_H
11 #define MPLAYER_NETSTREAM_H
13 #include "config.h"
14 #include <stdint.h>
15 #include <stdlib.h>
16 #include <string.h>
17 #include <errno.h>
18 #if !HAVE_WINSOCK2_H
19 #include <sys/socket.h>
20 #endif
21 #include "mp_msg.h"
22 #include "mpbswap.h"
24 typedef struct mp_net_stream_packet_st {
25 uint16_t len;
26 uint8_t cmd;
27 char data[0];
28 } __attribute__ ((packed)) mp_net_stream_packet_t;
30 #define PACKET_MAX_SIZE 4096
32 // Commands sent by the client
33 #define NET_STREAM_OPEN 0
34 // data is the url
35 #define NET_STREAM_FILL_BUFFER 1
36 // data is an uint16 wich is the max len of the data to return
37 #define NET_STREAM_SEEK 3
38 // data is an uint64 wich the pos where to seek
39 #define NET_STREAM_CLOSE 4
40 // no data
41 #define NET_STREAM_RESET 5
42 // no data
44 // Server response
45 #define NET_STREAM_OK 128
46 // Data returned if open is successful
47 typedef struct mp_net_stream_opened_st {
48 uint32_t file_format;
49 uint32_t flags;
50 uint32_t sector_size;
51 uint64_t start_pos;
52 uint64_t end_pos;
53 } __attribute__ ((packed)) mp_net_stream_opened_t;
54 // FILL_BUFFER return the data
55 // CLOSE return nothing
56 #define NET_STREAM_ERROR 129
57 // Data is the error message (if any ;)
59 static int net_read(int fd, char* buf, int len) {
60 int r = 0;
61 while(len) {
62 r = recv(fd,buf,len,0);
63 if(r <= 0) {
64 if(errno == EINTR) continue;
65 if(r < 0)
66 mp_msg(MSGT_NETST,MSGL_ERR,"Read failed: %s\n",strerror(errno));
67 return 0;
69 len -= r;
70 buf += r;
72 return 1;
75 static mp_net_stream_packet_t* read_packet(int fd) {
76 uint16_t len;
77 mp_net_stream_packet_t* pack =
78 (mp_net_stream_packet_t*)malloc(sizeof(mp_net_stream_packet_t));
80 if(!net_read(fd,(char*)pack,sizeof(mp_net_stream_packet_t))) {
81 free(pack);
82 return NULL;
84 pack->len = le2me_16(pack->len);
86 if(pack->len < sizeof(mp_net_stream_packet_t)) {
87 mp_msg(MSGT_NETST,MSGL_WARN,"Got invalid packet (too small: %d)\n",pack->len);
88 free(pack);
89 return NULL;
91 if(pack->len > PACKET_MAX_SIZE) {
92 mp_msg(MSGT_NETST,MSGL_WARN,"Got invalid packet (too big: %d)\n",pack->len);
93 free(pack);
94 return NULL;
96 len = pack->len;
97 if(len > sizeof(mp_net_stream_packet_t)) {
98 pack = realloc(pack,len);
99 if(!pack) {
100 mp_msg(MSGT_NETST,MSGL_ERR,"Failed to get memory for the packet (%d bytes)\n",len);
101 return NULL;
103 if(!net_read(fd,pack->data,len - sizeof(mp_net_stream_packet_t)))
104 return NULL;
106 // printf ("Read packet %d %d %d\n",fd,pack->cmd,pack->len);
107 return pack;
110 static int net_write(int fd, char* buf, int len) {
111 int w;
112 while(len) {
113 w = send(fd,buf,len,0);
114 if(w <= 0) {
115 if(errno == EINTR) continue;
116 if(w < 0)
117 mp_msg(MSGT_NETST,MSGL_ERR,"Write failed: %s\n",strerror(errno));
118 return 0;
120 len -= w;
121 buf += w;
123 return 1;
126 static int write_packet(int fd, uint8_t cmd,char* data,int len) {
127 mp_net_stream_packet_t* pack = malloc(len + sizeof(mp_net_stream_packet_t));
129 if(len > 0 && data)
130 memcpy(pack->data,data,len);
131 pack->len = len + sizeof(mp_net_stream_packet_t);
132 pack->cmd = cmd;
134 // printf("Write packet %d %d (%p) %d\n",fd,cmd,data,len);
135 pack->len = le2me_16(pack->len);
136 if(net_write(fd,(char*)pack,pack->len)) {
137 free(pack);
138 return 1;
140 free(pack);
141 return 0;
144 static void net_stream_opened_2_me(mp_net_stream_opened_t* o) {
145 o->file_format = le2me_32(o->file_format);
146 o->flags = le2me_32(o->flags);
147 o->sector_size = le2me_32(o->sector_size);
148 o->start_pos = le2me_64(o->start_pos);
149 o->end_pos = le2me_64(o->end_pos);
152 #endif /* MPLAYER_NETSTREAM_H */