return 1;
}
-static int verify_path(const char *path, char **resolved_path)
+static int verify_path(const char *orig_path, char **resolved_path)
{
- const char *orig_path = path;
char c;
const char prefix[] = AFS_AUDIO_FILE_DIR "/";
+ const char *path = orig_path;
const size_t prefix_len = strlen(prefix);
- PARA_DEBUG_LOG("path: %s\n", path);
c = *path++;
if (!c)
- return -E_BAD_PATH;
+ goto bad_path;
while (c) {
if (c == '/') {
c = *path++;
switch (c) {
default:
continue;
- case '/': case '\0':
- break;
+ case '/': /* double slash */
+ goto bad_path;
case '.':
- if (verify_dotfile(path) > 0)
- continue;
+ if (verify_dotfile(path) < 0)
+ goto bad_path;
}
- *resolved_path = NULL;
- return -E_BAD_PATH;
}
c = *path++;
}
- if (*orig_path == '/')
- *resolved_path = prefix_path("", 0, orig_path);
- else
+ if (*orig_path != '/')
*resolved_path = prefix_path(prefix, prefix_len, orig_path);
- PARA_DEBUG_LOG("resolved: %s\n", *resolved_path);
- return *resolved_path? 1: -E_BAD_PATH;
+ else
+ *resolved_path = para_strdup(orig_path);
+ return 1;
+bad_path:
+ return -E_BAD_PATH;
}
enum afhi_offsets {
}
/** The offsets of the data contained in the AFTCOL_CHUNKS column. */
-enum chunk_info_offsets {
+enum chunk_info_offsets{
/** The total number of chunks (4 bytes). */
CHUNKS_TOTAL_OFFSET = 0,
/** The length of the audio file header (4 bytes). */
return 1;
}
-
static int add_one_audio_file(const char *arg, const void *private_data)
{
int ret;
struct audio_format_info afhi, *afhi_ptr = NULL;
struct osl_row *pb = NULL, *hs = NULL; /* path brother/hash sister */
struct osl_object map, obj = {.data = NULL}, query, result;
- char *path;
+ char *path = NULL;
HASH_TYPE hash[HASH_SIZE];
afhi.header_offset = 0;
afhi.header_len = 0;
ret = verify_path(arg, &path);
if (ret < 0)
- return ret;
+ goto out_free;
query.data = path;
query.size = strlen(path) + 1;
ret = send_callback_request(path_brother_callback, &query, &result);
munmap(map.data, map.size);
out_free:
if (ret < 0)
- send_va_buffer(pad->fd, "failed to add %s (%s)\n", path,
- PARA_STRERROR(-ret));
+ send_va_buffer(pad->fd, "failed to add %s (%s)\n", path?
+ path : arg, PARA_STRERROR(-ret));
free(obj.data);
free(path);
if (afhi_ptr)
if (argc <= i)
return -E_AFT_SYNTAX;
for (; i < argc; i++) {
- ret = stat(argv[i], &statbuf);
+ char *path = para_strdup(argv[i]);
+ size_t len = strlen(path);
+ while (len > 1 && path[--len] == '/')
+ path[len] = '\0';
+ ret = stat(path, &statbuf);
if (ret < 0)
- return -E_AFS_STAT;
- if (S_ISDIR(statbuf.st_mode)) {
- ret = for_each_file_in_dir(argv[i],
- add_one_audio_file, &pad);
- continue;
- }
- ret = add_one_audio_file(argv[i], &pad);
+ PARA_NOTICE_LOG("failed to stat %s (%s)", path,
+ strerror(errno));
+ else
+ if (S_ISDIR(statbuf.st_mode))
+ for_each_file_in_dir(path, add_one_audio_file,
+ &pad);
+ else
+ add_one_audio_file(path, &pad);
+ free(path);
}
ret = 1;
return ret;
PARA_ERROR(BAD_AFS, "fixme"), \
PARA_ERROR(LOCALTIME, "fixme"), \
PARA_ERROR(STRFTIME, "fixme"), \
- PARA_ERROR(BAD_PATH, "fixme"), \
+ PARA_ERROR(BAD_PATH, "invalid path"), \
PARA_ERROR(BAD_SORT, "fixme"), \
PARA_ERROR(FNMATCH, "fixme"), \
PARA_ERROR(NO_MATCH, "fixme"), \
PARA_ERROR(NO_AFHI, "fixme"), \
PARA_ERROR(AFT_SYNTAX, "syntax error"), \
- PARA_ERROR(AFS_STAT, "stat(2) failed"), \
PARA_ERROR(HASH_MISMATCH, "fixme"), \