Subversion Repositories shark

Rev

Go to most recent revision | Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 pj 1
/*
2
 *   httpget.c
3
 *
4
 *   Oliver Fromme  <oliver.fromme@heim3.tu-clausthal.de>
5
 *   Wed Apr  9 20:57:47 MET DST 1997
6
 */
7
 
8
#include <stdlib.h>
9
#include <stdio.h>
10
#include <string.h>
11
#include <netdb.h>
12
#include <sys/param.h>
13
#include <sys/types.h>
14
#include <sys/socket.h>
15
#include <netinet/in.h>
16
#include <arpa/inet.h>
17
#include <sys/errno.h>
18
extern int errno;
19
 
20
#include "mpg123.h"
21
 
22
#ifndef INADDR_NONE
23
#define INADDR_NONE 0xffffffff
24
#endif
25
 
26
void writestring (int fd, char *string)
27
{
28
        int result, bytes = strlen(string);
29
 
30
        while (bytes) {
31
                if ((result = write(fd, string, bytes)) < 0 && errno != EINTR) {
32
                        perror ("write");
33
                        exit (1);
34
                }
35
                else if (result == 0) {
36
                        fprintf (stderr, "write: %s\n",
37
                                "socket closed unexpectedly");
38
                        exit (1);
39
                }
40
                string += result;
41
                bytes -= result;
42
        }
43
}
44
 
45
void readstring (char *string, int maxlen, FILE *f)
46
{
47
        char *result;
48
 
49
        do {
50
                result = fgets(string, maxlen, f);
51
        } while (!result  && errno == EINTR);
52
        if (!result) {
53
                fprintf (stderr, "Error reading from socket or unexpected EOF.\n");
54
                exit (1);
55
        }
56
}
57
 
58
char *url2hostport (char *url, char **hname, unsigned long *hip, unsigned int *port)
59
{
60
        char *cptr;
61
        struct hostent *myhostent;
62
        struct in_addr myaddr;
63
        int isip = 1;
64
 
65
        if (!(strncmp(url, "http://", 7)))
66
                url += 7;
67
        cptr = url;
68
        while (*cptr && *cptr != ':' && *cptr != '/') {
69
                if ((*cptr < '0' || *cptr > '9') && *cptr != '.')
70
                        isip = 0;
71
                cptr++;
72
        }
73
        if (!(*hname = strndup(url, cptr - url))) {
74
                *hname = NULL;
75
                return (NULL);
76
        }
77
        if (!isip) {
78
                if (!(myhostent = gethostbyname(*hname)))
79
                        return (NULL);
80
                memcpy (&myaddr, myhostent->h_addr, sizeof(myaddr));
81
                *hip = myaddr.s_addr;
82
        }
83
        else
84
                if ((*hip = inet_addr(*hname)) == INADDR_NONE)
85
                        return (NULL);
86
        if (!*cptr || *cptr == '/') {
87
                *port = 80;
88
                return (cptr);
89
        }
90
        *port = atoi(++cptr);
91
        while (*cptr && *cptr != '/')
92
                cptr++;
93
        return (cptr);
94
}
95
 
96
char *proxyurl = NULL;
97
unsigned long proxyip = 0;
98
unsigned int proxyport;
99
 
100
#define ACCEPT_HEAD "Accept: audio/mpeg, audio/x-mpegurl, */*\r\n"
101
 
102
FILE *http_open (char *url)
103
{
104
        char *purl, *host, *request, *sptr;
105
        int linelength;
106
        unsigned long myip;
107
        unsigned int myport;
108
        int sock;
109
        int relocate, numrelocs = 0;
110
        struct sockaddr_in server;
111
        FILE *myfile;
112
 
113
        if (!proxyip) {
114
                if (!proxyurl)
115
                        if (!(proxyurl = getenv("MP3_HTTP_PROXY")))
116
                                if (!(proxyurl = getenv("http_proxy")))
117
                                        proxyurl = getenv("HTTP_PROXY");
118
                if (proxyurl && proxyurl[0] && strcmp(proxyurl, "none")) {
119
                        if (!(url2hostport(proxyurl, &host, &proxyip, &proxyport))) {
120
                                fprintf (stderr, "Unknown proxy host \"%s\".\n",
121
                                        host ? host : "");
122
                                exit (1);
123
                        }
124
                        if (host)
125
                                free (host);
126
                }
127
                else
128
                        proxyip = INADDR_NONE;
129
        }
130
 
131
        if ((linelength = strlen(url)+200) < 1024)
132
                linelength = 1024;
133
        if (!(request = malloc(linelength)) || !(purl = malloc(1024))) {
134
                fprintf (stderr, "malloc() failed, out of memory.\n");
135
                exit (1);
136
        }
137
        strncpy (purl, url, 1023);
138
        purl[1023] = '\0';
139
        do {
140
                strcpy (request, "GET ");
141
                if (proxyip != INADDR_NONE) {
142
                        if (strncmp(url, "http://", 7))
143
                                strcat (request, "http://");
144
                        strcat (request, purl);
145
                        myport = proxyport;
146
                        myip = proxyip;
147
                }
148
                else {
149
                        if (!(sptr = url2hostport(purl, &host, &myip, &myport))) {
150
                                fprintf (stderr, "Unknown host \"%s\".\n",
151
                                        host ? host : "");
152
                                exit (1);
153
                        }
154
                        if (host)
155
                                free (host);
156
                        strcat (request, sptr);
157
                }
158
                sprintf (request + strlen(request),
159
                        " HTTP/1.0\r\nUser-Agent: %s/%s\r\n",
160
                        prgName, prgVersion);
161
                strcat (request, ACCEPT_HEAD);
162
                strcat (request, "\r\n");
163
                server.sin_family = AF_INET;
164
                server.sin_port = htons(myport);
165
                server.sin_addr.s_addr = myip;
166
                if ((sock = socket(PF_INET, SOCK_STREAM, 6)) < 0) {
167
                        perror ("socket");
168
                        exit (1);
169
                }
170
                if (connect(sock, (struct sockaddr *)&server, sizeof(server))) {
171
                        perror ("connect");
172
                        exit (1);
173
                }
174
                writestring (sock, request);
175
                if (!(myfile = fdopen(sock, "rb"))) {
176
                        perror ("fdopen");
177
                        exit (1);
178
                };
179
                relocate = FALSE;
180
                purl[0] = '\0';
181
                readstring (request, linelength-1, myfile);
182
                if ((sptr = strchr(request, ' '))) {
183
                        switch (sptr[1]) {
184
                                case '3':
185
                                        relocate = TRUE;
186
                                case '2':
187
                                        break;
188
                                default:
189
                                        fprintf (stderr, "HTTP request failed: %s",
190
                                                sptr+1); /* '\n' is included */
191
                                        exit (1);
192
                        }
193
                }
194
                do {
195
                        readstring (request, linelength-1, myfile);
196
                        if (!strncmp(request, "Location:", 9))
197
                                strncpy (purl, request+10, 1023);
198
                } while (request[0] != '\r' && request[0] != '\n');
199
        } while (relocate && purl[0] && numrelocs++ < 5);
200
        if (relocate) {
201
                fprintf (stderr, "Too many HTTP relocations.\n");
202
                exit (1);
203
        }
204
        free (purl);
205
        free (request);
206
        return (myfile);
207
}
208
 
209
/* EOF */