1/* 2 * Buffered file io for ffmpeg system 3 * Copyright (c) 2001 Fabrice Bellard 4 * 5 * This file is part of FFmpeg. 6 * 7 * FFmpeg is free software; you can redistribute it and/or 8 * modify it under the terms of the GNU Lesser General Public 9 * License as published by the Free Software Foundation; either 10 * version 2.1 of the License, or (at your option) any later version. 11 * 12 * FFmpeg is distributed in the hope that it will be useful, 13 * but WITHOUT ANY WARRANTY; without even the implied warranty of 14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 15 * Lesser General Public License for more details. 16 * 17 * You should have received a copy of the GNU Lesser General Public 18 * License along with FFmpeg; if not, write to the Free Software 19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 20 */ 21 22#include "libavutil/avstring.h" 23#include "avformat.h" 24#include <fcntl.h> 25#if HAVE_SETMODE 26#include <io.h> 27#endif 28#include <unistd.h> 29#include <sys/stat.h> 30#include <sys/time.h> 31#include <stdlib.h> 32#include "os_support.h" 33 34 35/* standard file protocol */ 36 37static int file_open(URLContext *h, const char *filename, int flags) 38{ 39 int access; 40 int fd; 41 42 av_strstart(filename, "file:", &filename); 43 44 if (flags & URL_RDWR) { 45 access = O_CREAT | O_TRUNC | O_RDWR; 46 } else if (flags & URL_WRONLY) { 47 access = O_CREAT | O_TRUNC | O_WRONLY; 48 } else { 49 access = O_RDONLY; 50 } 51#ifdef O_BINARY 52 access |= O_BINARY; 53#endif 54 fd = open(filename, access, 0666); 55 if (fd == -1) 56 return AVERROR(errno); 57 h->priv_data = (void *) (intptr_t) fd; 58 return 0; 59} 60 61static int file_read(URLContext *h, unsigned char *buf, int size) 62{ 63 int fd = (intptr_t) h->priv_data; 64 return read(fd, buf, size); 65} 66 67static int file_write(URLContext *h, unsigned char *buf, int size) 68{ 69 int fd = (intptr_t) h->priv_data; 70 return write(fd, buf, size); 71} 72 73/* XXX: use llseek */ 74static int64_t file_seek(URLContext *h, int64_t pos, int whence) 75{ 76 int fd = (intptr_t) h->priv_data; 77 if (whence == AVSEEK_SIZE) { 78 struct stat st; 79 int ret = fstat(fd, &st); 80 return ret < 0 ? AVERROR(errno) : st.st_size; 81 } 82 return lseek(fd, pos, whence); 83} 84 85static int file_close(URLContext *h) 86{ 87 int fd = (intptr_t) h->priv_data; 88 return close(fd); 89} 90 91static int file_get_handle(URLContext *h) 92{ 93 return (intptr_t) h->priv_data; 94} 95 96URLProtocol file_protocol = { 97 "file", 98 file_open, 99 file_read, 100 file_write, 101 file_seek, 102 file_close, 103 .url_get_file_handle = file_get_handle, 104}; 105 106/* pipe protocol */ 107 108static int pipe_open(URLContext *h, const char *filename, int flags) 109{ 110 int fd; 111 char *final; 112 av_strstart(filename, "pipe:", &filename); 113 114 fd = strtol(filename, &final, 10); 115 if((filename == final) || *final ) {/* No digits found, or something like 10ab */ 116 if (flags & URL_WRONLY) { 117 fd = 1; 118 } else { 119 fd = 0; 120 } 121 } 122#if HAVE_SETMODE 123 setmode(fd, O_BINARY); 124#endif 125 h->priv_data = (void *) (intptr_t) fd; 126 h->is_streamed = 1; 127 return 0; 128} 129 130URLProtocol pipe_protocol = { 131 "pipe", 132 pipe_open, 133 file_read, 134 file_write, 135 .url_get_file_handle = file_get_handle, 136}; 137