A modern Music Player Daemon based on Rockbox open source high quality audio player
libadwaita audio rust zig deno mpris rockbox mpd
at master 211 lines 5.4 kB view raw
1/* zenutils - Utilities for working with creative firmwares. 2 * Copyright 2007 (c) Rasmus Ry <rasmus.ry{at}gmail.com> 3 * 4 * This program is free software; you can redistribute it and/or modify 5 * it under the terms of the GNU General Public License as published by 6 * the Free Software Foundation; either version 2 of the License, or 7 * (at your option) any later version. 8 * 9 * This program is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 * GNU General Public License for more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with this program; if not, write to the Free Software 16 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 17 */ 18 19#include "utils.h" 20#include <fstream> 21#include <zlib/zlib.h> 22 23 24std::string shared::replace_extension(const std::string& filename, const std::string& extension) 25{ 26 std::string newname; 27 const char* name = filename.c_str(); 28 const char* ext = strrchr(name, '.'); 29 if (ext) 30 { 31 // If an extension was found, replace it. 32 newname.assign(name, ext-name); 33 newname += extension; 34 } 35 else 36 { 37 // If an extension was not found, append it. 38 newname = name; 39 newname += extension; 40 } 41 return newname; 42} 43 44std::string shared::remove_extension(const std::string& filename) 45{ 46 std::string newname; 47 const char* name = filename.c_str(); 48 const char* ext = strrchr(name, '.'); 49 if (ext) 50 { 51 newname.assign(name, ext-name); 52 } 53 else 54 { 55 newname = name; 56 } 57 return newname; 58} 59 60std::string shared::double_quote(const std::string& str) 61{ 62 std::string out; 63 for (int i = 0, j = str.length(); i < j; i++) 64 { 65 if (str[i] == '\\') 66 out += "\\\\"; 67 else 68 out += str[i]; 69 } 70 return out; 71} 72 73bool shared::inflate_to_file(const bytes& buffer, const char* filename) 74{ 75 // Open output file. 76 std::ofstream ofs; 77 ofs.open(filename, std::ios::binary); 78 if (!ofs) 79 { 80 return false; 81 } 82 83 // Initialize zlib. 84 z_stream d_stream; // decompression stream 85 86 d_stream.zalloc = Z_NULL; 87 d_stream.zfree = Z_NULL; 88 d_stream.opaque = Z_NULL; 89 90 d_stream.next_in = const_cast<bytes::value_type*>(&buffer[0]); 91 d_stream.avail_in = static_cast<uInt>(buffer.size()); 92 93 int ret = inflateInit(&d_stream); 94 if (ret != Z_OK) 95 return false; 96 97 // Allocate buffer to hold the inflated data. 98 const size_t BUFSIZE = 1048576; 99 Bytef* infbuf = new Bytef[BUFSIZE]; 100 if (!infbuf) 101 return false; 102 103 // Decompress untill the end of the input buffer. 104 uLong totalout = 0; 105 bool bLoop = true; 106 while (bLoop) 107 { 108 d_stream.next_out = infbuf; 109 d_stream.avail_out = BUFSIZE; 110 111 ret = inflate(&d_stream, Z_NO_FLUSH); 112 if (ret == Z_STREAM_END) 113 { 114 bLoop = false; 115 } 116 else if (ret != Z_OK) 117 { 118 inflateEnd(&d_stream); 119 delete [] infbuf; 120 return false; 121 } 122 123 // Write the inflated data to the output file. 124 if (!ofs.write((const char*)infbuf, d_stream.total_out-totalout)) 125 { 126 inflateEnd(&d_stream); 127 delete [] infbuf; 128 return false; 129 } 130 totalout = d_stream.total_out; 131 } 132 133 // Cleanup and return. 134 inflateEnd(&d_stream); 135 delete [] infbuf; 136 137 return true; 138} 139 140bool shared::deflate_to_file(const bytes& buffer, const char* filename) 141{ 142 // Open output file. 143 std::ofstream ofs; 144 ofs.open(filename, std::ios::binary); 145 if (!ofs) 146 { 147 return false; 148 } 149 150 // Initialize zlib. 151 z_stream c_stream; // compression stream. 152 153 c_stream.zalloc = Z_NULL; 154 c_stream.zfree = Z_NULL; 155 c_stream.opaque = Z_NULL; 156 157 int ret = deflateInit(&c_stream, Z_BEST_COMPRESSION); 158 if (ret != Z_OK) 159 return false; 160 161 // Allocate buffer to hold the deflated data. 162 const size_t BUFSIZE = 1048576; 163 Bytef* defbuf = new Bytef[BUFSIZE]; 164 if (!defbuf) 165 return false; 166 167 c_stream.avail_in = static_cast<uInt>(buffer.size()); 168 c_stream.next_in = const_cast<bytes::value_type*>(&buffer[0]); 169 170 // Compress until end of the buffer. 171 uLong totalout = 0; 172 bool bLoop = true; 173 while (bLoop) 174 { 175 c_stream.avail_out = BUFSIZE; 176 c_stream.next_out = defbuf; 177 178 ret = deflate(&c_stream, Z_NO_FLUSH); // no bad return value 179 if (ret == Z_STREAM_END) 180 { 181 bLoop = false; 182 } 183 else if (ret == Z_BUF_ERROR && !c_stream.avail_in) 184 { 185 ret = deflate(&c_stream, Z_FINISH); // no bad return value 186 bLoop = false; 187 } 188 else if (ret != Z_OK) 189 { 190 deflateEnd(&c_stream); 191 delete [] defbuf; 192 return false; 193 } 194 195 // Write the inflated data to the output file. 196 if (!ofs.write((const char*)defbuf, c_stream.total_out-totalout)) 197 { 198 deflateEnd(&c_stream); 199 delete [] defbuf; 200 return false; 201 } 202 203 totalout = c_stream.total_out; 204 } 205 206 // Clean up and return. 207 deflateEnd(&c_stream); 208 delete [] defbuf; 209 210 return true; 211}