A modern Music Player Daemon based on Rockbox open source high quality audio player
libadwaita audio rust zig deno mpris rockbox mpd
at master 253 lines 5.0 kB view raw
1/*************************************************************************** 2 * __________ __ ___. 3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___ 4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / 5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < 6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ 7 * \/ \/ \/ \/ \/ 8 * 9 * Copyright (C) 2013 by Marcin Bukat 10 * 11 * This program is free software; you can redistribute it and/or 12 * modify it under the terms of the GNU General Public License 13 * as published by the Free Software Foundation; either version 2 14 * of the License, or (at your option) any later version. 15 * 16 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY 17 * KIND, either express or implied. 18 * 19 ****************************************************************************/ 20 21#include "plugin.h" 22#include "stdio_compat.h" 23#include "errno.h" 24 25static _FILE_ __file__[MAX_STDIO_FILES] = { 26 {-1,-1,0},{-1,-1,0},{-1,-1,0},{-1,-1,0}, 27 {-1,-1,0},{-1,-1,0},{-1,-1,0},{-1,-1,0}, 28 {-1,-1,0},{-1,-1,0},{-1,-1,0} 29}; 30 31_FILE_ *_stdout_ = NULL, *_stderr_ = NULL; 32 33_FILE_ *_fopen_(const char *path, const char *mode) 34{ 35 _FILE_ *f = __file__; 36 int flags = O_RDONLY; 37 int fd = -1; 38 int i; 39 40 /* look for free slot */ 41 for (i=0; i<MAX_STDIO_FILES; i++, f++) 42 if (f->fd == -1) 43 break; 44 45 /* no empty slots */ 46 if (i == MAX_STDIO_FILES) 47 { 48 rb->splash(HZ, "no open slots"); 49 return NULL; 50 } 51 52 if (*mode != 'r') 53 { 54 /* Not read */ 55 flags = (O_WRONLY | O_CREAT | O_TRUNC); 56 if (*mode != 'w') 57 { 58 /* Not write (create of append) */ 59 flags = (O_WRONLY | O_CREAT | O_APPEND); 60 if (*mode != 'a') 61 { 62 /* Illegal */ 63 return NULL; 64 } 65 } 66 } 67 68 if (mode[1] == 'b') 69 { 70 /* Ignore */ 71 mode++; 72 } 73 74 if (mode[1] == '+') 75 { 76 /* Read and Write. */ 77 flags |= (O_RDONLY | O_WRONLY); 78 flags += (O_RDWR - (O_RDONLY | O_WRONLY)); 79 } 80 81 82 fd = rb->open(path, flags, 0666); 83 84 if (fd < 0) 85 { 86 return NULL; 87 } 88 89 /* initialize */ 90 f->fd = fd; 91 f->unget_char = -1; 92 93 return f; 94} 95 96int _fflush_(_FILE_ *stream) 97{ 98 (void)stream; 99 /* no buffering so we are always in sync */ 100 return 0; 101} 102 103size_t _fread_(void *ptr, size_t size, size_t nmemb, _FILE_ *stream) 104{ 105 ssize_t ret = rb->read(stream->fd, (char *)ptr, size*nmemb); 106 107 if (ret < (ssize_t)(size*nmemb)) 108 stream->error = -1; 109 return ret / size; 110} 111 112size_t _fwrite_(const void *ptr, size_t size, size_t nmemb, _FILE_ *stream) 113{ 114 if(stream) 115 { 116 ssize_t ret = rb->write(stream->fd, ptr, size*nmemb); 117 118 if (ret < (ssize_t)(size*nmemb)) 119 stream->error = -1; 120 121 return ret / size; 122 } 123 /* stderr, stdout (disabled) */ 124 else 125 { 126 return size * nmemb; 127 } 128} 129 130int _fseek_(_FILE_ *stream, long offset, int whence) 131{ 132 if(rb->lseek(stream->fd, offset, whence) >= 0) 133 return 0; 134 else 135 { 136 rb->splashf(HZ, "lseek() failed: %d fd:%d", errno, stream->fd); 137 return -1; 138 } 139} 140 141long _ftell_(_FILE_ *stream) 142{ 143 return rb->lseek(stream->fd, 0, SEEK_CUR); 144} 145 146int _fclose_(_FILE_ *stream) 147{ 148 if (stream->fd == -1) 149 return EOF; 150 151 if (rb->close(stream->fd) == -1) 152 return EOF; 153 154 /* free the resource */ 155 stream->fd = -1; 156 157 return 0; 158} 159 160int _fgetc_(_FILE_ *stream) 161{ 162 unsigned char c; 163 164 if (stream->unget_char != -1) 165 { 166 c = stream->unget_char; 167 stream->unget_char = -1; 168 return c; 169 } 170 171 if ( rb->read(stream->fd, &c, 1) != 1) 172 return EOF; 173 174 return c; 175} 176 177int _ungetc_(int c, _FILE_ *stream) 178{ 179 stream->unget_char = c; 180 181 return c; 182} 183 184int _fputc_(int c, _FILE_ *stream) 185{ 186 unsigned char cb = c; 187 188 if (rb->write(stream->fd, &cb, 1) != 1) 189 return EOF; 190 191 return cb; 192} 193 194char *_fgets_(char *s, int size, _FILE_ *stream) 195{ 196 char *p = s; 197 char c = '\0'; 198 199 for (int i=0; i<size; i++) 200 { 201 if ( rb->read(stream->fd, &c, 1) != 1) 202 break; 203 204 *p++ = c; 205 206 if (c == '\n') 207 break; 208 } 209 210 if (p == s) 211 return NULL; 212 213 *p = '\0'; 214 215 return s; 216} 217 218void _clearerr_(_FILE_ *stream) 219{ 220 if (stream) 221 stream->error = 0; 222} 223 224int _ferror_(_FILE_ *stream) 225{ 226 return (stream) ? stream->error : -1; 227} 228 229int _feof_(_FILE_ *stream) 230{ 231 int c = _fgetc_(stream); 232 233 if (c != EOF) 234 { 235 _ungetc_(c, stream); 236 return 0; 237 } 238 239 return 0; 240} 241 242int _fprintf_(_FILE_ *stream, const char *format, ...) 243{ 244 int len; 245 va_list ap; 246 char buf[256]; 247 248 va_start(ap, format); 249 len = rb->vsnprintf(buf, sizeof(buf), format, ap); 250 va_end(ap); 251 252 return _fwrite_(buf, 1, len, stream); 253}