40#define VAL_OR_EMPTY(val) ((val) != nullptr ? (val) : "")
97static bool create_cuesheet_virtualfile(
LPCVIRTUALFILE virtualfile, Track *track,
int titleno,
const std::string & path,
const struct stat * statbuf,
int trackcount,
int trackno,
const std::string &aperformer,
const std::string & album,
const std::string & genre,
const std::string & date, int64_t *remainingduration,
LPVIRTUALFILE *lastfile);
100static int parse_cuesheet(
LPCVIRTUALFILE virtualfile,
const std::string & cuesheet, Cd *cd,
const struct stat *statbuf,
void *buf, fuse_fill_dir_t filler);
119static bool create_cuesheet_virtualfile(
LPCVIRTUALFILE virtualfile, Track *track,
int titleno,
const std::string & path,
const struct stat * statbuf,
int trackcount,
int trackno,
const std::string & aperformer,
const std::string & album,
const std::string & genre,
const std::string & date, int64_t *remainingduration,
LPVIRTUALFILE *lastfile)
121 Cdtext *cuesheetcdtext = track_get_cdtext(track);
122 if (cuesheetcdtext ==
nullptr)
124 Logging::error(virtualfile->m_origfile,
"The track CD text could not be extracted from the cue sheet.");
129 std::string performer =
VAL_OR_EMPTY(cdtext_get(PTI_PERFORMER, cuesheetcdtext));
130 std::string title =
VAL_OR_EMPTY(cdtext_get(PTI_TITLE, cuesheetcdtext));
132 if (performer.empty())
135 performer = aperformer;
138 int64_t start = AV_TIME_BASE *
static_cast<int64_t
>(track_get_start(track)) /
FPS;
139 int64_t length = track_get_length(track);
144 duration = AV_TIME_BASE * length /
FPS;
145 *remainingduration -= duration;
150 duration = *remainingduration;
153 std::string virtfilename;
155 strsprintf(&virtfilename,
"%02d. %s - %s [%s].%s",
163 std::replace(virtfilename.begin(), virtfilename.end(),
'/',
'-');
175 if (newvirtualfile ==
nullptr)
177 Logging::error(path,
"Failed to create virtual path: %1", (path + virtfilename).c_str());
185 newvirtualfile->
m_format_idx = virtualfile->m_format_idx;
194 AVRational framerate = { 0, 0 };
195 bool interleaved =
false;
207 if (*lastfile !=
nullptr)
209 (*lastfile)->m_cuesheet_track.m_nextfile = newvirtualfile;
211 *lastfile = newvirtualfile;
213 transcoder_set_filesize(newvirtualfile, duration, audio_bit_rate, virtualfile->
m_channels, virtualfile->m_sample_rate, AV_SAMPLE_FMT_NONE, video_bit_rate, width, height, interleaved, framerate);
243 return parse_cuesheet(virtualfile, cuesheet, cue_parse_string(text.c_str()), statbuf, buf, filler);
256 Logging::trace(virtualfile->m_origfile,
"Found an embedded cue sheet file.");
258 return parse_cuesheet(virtualfile, virtualfile->m_origfile, cue_parse_string(virtualfile->m_cuesheet.c_str()), &virtualfile->m_st, buf, filler);
271static int parse_cuesheet(
LPCVIRTUALFILE virtualfile,
const std::string & cuesheet, Cd *cd,
const struct stat *statbuf,
void *buf, fuse_fill_dir_t filler)
283 Rem *rem = cd_get_rem(cd);
286 Logging::error(cuesheet,
"Unable to parse remarks from the cue sheet.");
290 Cdtext *cdtext = cd_get_cdtext(cd);
291 if (cdtext ==
nullptr)
293 Logging::error(cuesheet,
"The CD text could not be extracted from the cue sheet.");
297 std::string performer =
VAL_OR_EMPTY(cdtext_get(PTI_PERFORMER, cdtext));
298 std::string album =
VAL_OR_EMPTY(cdtext_get(PTI_TITLE, cdtext));
299 std::string genre =
VAL_OR_EMPTY(cdtext_get(PTI_GENRE, cdtext));
300 std::string date =
VAL_OR_EMPTY(rem_get(REM_DATE, rem));
302 int trackcount =
static_cast<int>(cd_get_ntrack(cd));
306 std::string subbdir(virtualfile->m_origfile);
310 std::string dirname(subbdir);
317 if (insertedvirtualfile ==
nullptr)
319 Logging::error(cuesheet,
"Failed to create virtual path: %1", subbdir.c_str());
324 if (buf !=
nullptr && filler(buf, dirname.c_str(), &insertedvirtualfile->
m_st, 0))
329 std::string path(virtualfile->m_origfile);
334 int64_t remainingduration = virtualfile->
m_duration;
336 for (
int trackno = 1; trackno <= trackcount; trackno++)
338 Track *track = cd_get_track(cd, trackno);
339 if (track ==
nullptr)
341 Logging::error(cuesheet,
"Track no. %1 could not be obtained from the cue sheet.", trackno);
346 if (!
create_cuesheet_virtualfile(virtualfile, track, trackno, path + dirname +
"/", statbuf, trackcount, trackno, performer, album, genre, date, &remainingduration, &lastfile))
368int check_cuesheet(
const std::string & filename,
void *buf, fuse_fill_dir_t filler)
370 std::string trackdir(filename);
371 std::string cuesheet(filename);
383 if (virtualfile ==
nullptr)
386 Logging::error(filename,
"INTERNAL ERROR: check_cuesheet()! virtualfile is NULL.");
391 if (stat(filename.c_str(), &stbuf) == -1)
397 if (stat(cuesheet.c_str(), &stbuf) != -1)
410 std::string dirname(trackdir);
416 if (virtualdir ==
nullptr)
418 Logging::error(filename,
"INTERNAL ERROR: check_cuesheet()! virtualdir is NULL.");
423 if (buf !=
nullptr && filler(buf, dirname.c_str(), &virtualdir->m_st, 0))
431 else if (!virtualfile->m_cuesheet.empty())
static void trace(const T filename, const std::string &format_string, Args &&...args)
Write trace level log entry.
static void error(const T filename, const std::string &format_string, Args &&...args)
Write error level log entry.
static bool create_cuesheet_virtualfile(LPCVIRTUALFILE virtualfile, Track *track, int titleno, const std::string &path, const struct stat *statbuf, int trackcount, int trackno, const std::string &aperformer, const std::string &album, const std::string &genre, const std::string &date, int64_t *remainingduration, LPVIRTUALFILE *lastfile)
Cuesheet structure Structure see https://en.wikipedia.org/wiki/Cue_sheet_(computing) Real life exam...
static int parse_cuesheet_text(LPCVIRTUALFILE virtualfile, void *buf, fuse_fill_dir_t filler)
Parse a cue sheet and build virtual set of files.
static int parse_cuesheet_file(LPCVIRTUALFILE virtualfile, const std::string &cuesheet, const struct stat *statbuf, void *buf, fuse_fill_dir_t filler)
Parse a cue sheet file and build virtual set of files.
static int parse_cuesheet(LPCVIRTUALFILE virtualfile, const std::string &cuesheet, Cd *cd, const struct stat *statbuf, void *buf, fuse_fill_dir_t filler)
Parse a cue sheet and build virtual set of files.
#define VAL_OR_EMPTY(val)
int check_cuesheet(const std::string &filename, void *buf, fuse_fill_dir_t filler)
Get number of titles in cue sheet.
const std::string & remove_path(std::string *filepath)
Remove path from filename. Handy basename alternative.
std::string format_duration(int64_t value, uint32_t fracs)
Format a time in format HH:MM:SS.fract.
int read_file(const std::string &path, std::string &result)
Read text file and return in UTF-8 format, no matter in which encoding the input file is....
const std::string & remove_filename(std::string *filepath)
Remove filename from path. Handy dirname alternative.
const std::string & replace_ext(std::string *filepath, const std::string &ext)
Replace extension in filename, taking into account that there might not be an extension already.
const std::string & append_ext(std::string *filepath, const std::string &ext)
Append extension to filename. If ext is the same as.
const std::string & append_sep(std::string *path)
Add / to the path if required.
void stat_set_size(struct stat *st, size_t size)
Properly fill in all size related members in stat struct.
std::string replace_all(std::string str, const std::string &from, const std::string &to)
Same as std::string replace(), but replaces all occurrences.
#define BITRATE
For FFmpeg bit rate is an int.
const std::string & strsprintf(std::string *str, const std::string &format, Args ... args)
Format a std::string sprintf-like.
@ VIDEO
FFmpegfs_Format info, 0: video file.
FFMPEGFS_FORMAT_ARR ffmpeg_format
Two FFmpegfs_Format infos, 0: video file, 1: audio file.
Main include for FFmpegfs project.
LPVIRTUALFILE find_file(const std::string &virtfile)
Find file in cache.
LPVIRTUALFILE insert_dir(VIRTUALTYPE type, const std::string &virtdir, const struct stat *stbuf, int flags=VIRTUALFLAG_NONE)
Add new virtual directory to the internal list. If the file already exists, it will be updated.
bool check_path(const std::string &path)
Check if the path has already been parsed. Only useful if for DVD, Blu-ray or VCD where it is guarant...
LPVIRTUALFILE find_file_from_orig(const std::string &origfile)
Look for the file in the cache.
LPVIRTUALFILE insert_file(VIRTUALTYPE type, const std::string &virtfile, const struct stat *stbuf, int flags=VIRTUALFLAG_NONE)
Add new virtual file to internal list.
@ DISK
Regular disk file to transcode.
#define VIRTUALFLAG_CUESHEET
File is part of a set of cue sheet tracks or the directory.
VIRTUALFILE const * LPCVIRTUALFILE
Pointer to const version of VIRTUALFILE.
Provide various log facilities to stderr, disk or syslog.
std::string m_artist
Track artist.
int64_t m_duration
Track/chapter duration, in AV_TIME_BASE fractional seconds.
std::string m_album
Album title.
std::string m_title
Track title.
int64_t m_start
Track start time, in AV_TIME_BASE fractional seconds.
int m_trackno
Track number.
int m_tracktotal
Total number of tracks in cue sheet.
std::string m_genre
Album genre.
std::string m_date
Publishing date.
size_t m_predicted_size
Use this as the size instead of computing it over and over.
int m_channels
Audio channels - Filled in for the DVD/Blu-ray directory.
struct stat m_st
stat structure with size etc.
size_t m_format_idx
Index into params.format[] array.
struct VIRTUALFILE::CUESHEET_TRACK m_cuesheet_track
Cue sheet data for track.
int64_t m_duration
Track/chapter duration, in AV_TIME_BASE fractional seconds.
bool transcoder_set_filesize(LPVIRTUALFILE virtualfile, int64_t duration, BITRATE audio_bit_rate, int channels, int sample_rate, AVSampleFormat sample_format, BITRATE video_bit_rate, int width, int height, bool interleaved, const AVRational &framerate)
Set the file size.
bool transcoder_cached_filesize(LPVIRTUALFILE virtualfile, struct stat *stbuf)
Simply get encoded file size (do not create the whole encoder/decoder objects)
File transcoder interface (for use with by FUSE)