int isourfile(char *fn) { /* Finally fixed */ if(StringComp(fn + strlen(fn) - 3, "aac", 3) == 0) { return 1; } return 0; }
int id3v2_tag(unsigned char *buffer) { if(StringComp((const char *)buffer, "ID3", 3) == 0) { unsigned long tagsize; // high bit is not used tagsize = (buffer[6] << 21) | (buffer[7] << 14) | (buffer[8] << 7) | (buffer[9] << 0); tagsize += 10; return tagsize; } return 0; }
FILE_STREAM *open_filestream(char *filename) { FILE_STREAM *fs; if(StringComp(filename,"http://", 7) == 0) { fs = (FILE_STREAM *)LocalAlloc(LPTR, sizeof(FILE_STREAM) + m_stream_buffer_size * 1024); if(fs == NULL) return NULL; fs->data = (unsigned char *)&fs[1]; if(http_file_open(filename, fs) < 0) { LocalFree(fs); return NULL; } fs->http = 1; } else { fs = (FILE_STREAM*)LocalAlloc(LPTR, sizeof(FILE_STREAM) + m_local_buffer_size * 1024); if(fs == NULL) return NULL; fs->data = (unsigned char *)&fs[1]; fs->stream = CreateFile(filename, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE, 0, OPEN_EXISTING, FILE_FLAG_SEQUENTIAL_SCAN, 0); if (fs->stream == INVALID_HANDLE_VALUE) { LocalFree(fs); return NULL; } fs->http = 0; } fs->buffer_length = 0; fs->buffer_offset = 0; fs->file_offset = 0; return fs; }
int http_file_open(char *url, FILE_STREAM *fs) { SOCKET sck; SOCKADDR_IN host; char server[1024], file[1024], request[1024], *temp = NULL, *tmpfile = NULL; int i, j, port = 80, bytes_recv, http_code; /* No winsock, no streaming */ if(!winsock_init) { return -1; } url += 7; // Skip over http:// /* Extract data from the URL */ for(i=0; url[i] != '/' && url[i] != ':' && url[i] != 0; i++); ZeroMemory(server, 1024); CopyMemory(server, url, i); if(url[i] == ':') { /* A certain port was specified */ port = atol(url + (i + 1)); } for(; url[i] != '/' && url[i] != 0; i++); ZeroMemory(file, 1024); CopyMemory(file, url + i, lstrlen(url)); /* END OF URL PARSING */ /* Create a TCP/IP socket */ sck = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); if(sck == INVALID_SOCKET) { CommonExit("Error creating TCP/IP new socket"); return -1; } /* Resolve the host address (turn www.blah.com into an IP) */ if(resolve_host(server, &host, (unsigned short)port)) { CommonExit("Error resolving host address"); CloseTCP(sck); return -1; } /* Connect to the server */ if(connect(sck, (SOCKADDR *)&host, sizeof(SOCKADDR)) == SOCKET_ERROR) { CommonExit("Error connecting to remote server"); CloseTCP(sck); return -1; } tmpfile = calloc(1, (strlen(file) * 3) + 1); /* Encode URL */ for(i=0, j=0; i < (int)strlen(file); i++) { if((unsigned char)file[i] <= 31 || (unsigned char)file[i] >= 127) { /* encode ASCII-control characters */ wsprintf(tmpfile + j, "%%%X", (unsigned char)file[i]); j += 3; continue; } else { switch(file[i]) { /* encode characters that could confuse some servers */ case ' ': case '"': case '>': case '<': case '#': case '%': case '{': case '}': case '|': case '\\': case '^': case '~': case '[': case ']': case '`': wsprintf(tmpfile + j, "%%%X", (unsigned char)file[i]); j += 3; continue; } } tmpfile[j] = file[i]; j++; } wsprintf(request, "GET %s\r\n\r\n", tmpfile); free(tmpfile); /* Send the request */ if(send(sck, request, lstrlen(request), 0) <= 0) { /* Error sending data */ CloseTCP(sck); return -1; } ZeroMemory(request, 1024); /* Send the request */ if((bytes_recv = recv(sck, request, 1024, 0)) <= 0) { /* Error sending data */ CloseTCP(sck); return -1; } if(StringComp(request,"HTTP/1.", 7) != 0) { /* Invalid header */ CloseTCP(sck); return -1; } http_code = atol(request + 9); if(http_code < 200 || http_code > 299) { /* HTTP error */ CloseTCP(sck); return -1; } // Search for a length field fs->http_file_length = 0; /* Limit search to only 20 loops */ if((temp = strstr(request, "Content-Length: ")) != NULL) { /* Has a content-length field, copy into structure */ fs->http_file_length = atol(temp + 16); } /* Copy the handle data into the structure */ fs->inetStream = sck; /* Copy any excess data beyond the header into the filestream buffers */ temp = strstr(request, "\r\n\r\n"); if(temp) { temp += 4; } if(temp - request < bytes_recv) { memcpy(fs->data, temp, (temp - request) - bytes_recv); fs->buffer_length = (temp - request) - bytes_recv; fs->buffer_offset = 0; } return 0; }