|
Packit Service |
a9274b |
// SPDX-License-Identifier: GPL-2.0
|
|
Packit Service |
a9274b |
//
|
|
Packit Service |
a9274b |
// mapper.c - an interface of muxer/demuxer between buffer with data frames and
|
|
Packit Service |
a9274b |
// formatted files.
|
|
Packit Service |
a9274b |
//
|
|
Packit Service |
a9274b |
// Copyright (c) 2018 Takashi Sakamoto <o-takashi@sakamocchi.jp>
|
|
Packit Service |
a9274b |
//
|
|
Packit Service |
a9274b |
// Licensed under the terms of the GNU General Public License, version 2.
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
#include "mapper.h"
|
|
Packit Service |
a9274b |
#include "misc.h"
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
#include <stdio.h>
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
static const char *const mapper_type_labels[] = {
|
|
Packit Service |
a9274b |
[MAPPER_TYPE_MUXER] = "muxer",
|
|
Packit Service |
a9274b |
[MAPPER_TYPE_DEMUXER] = "demuxer",
|
|
Packit Service |
a9274b |
};
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
static const char *const mapper_target_labels[] = {
|
|
Packit Service |
a9274b |
[MAPPER_TARGET_SINGLE] = "single",
|
|
Packit Service |
a9274b |
[MAPPER_TARGET_MULTIPLE] = "multiple",
|
|
Packit Service |
a9274b |
};
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
int mapper_context_init(struct mapper_context *mapper,
|
|
Packit Service |
a9274b |
enum mapper_type type, unsigned int cntr_count,
|
|
Packit Service |
a9274b |
unsigned int verbose)
|
|
Packit Service |
a9274b |
{
|
|
Packit Service |
a9274b |
const struct mapper_data *data = NULL;
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
assert(mapper);
|
|
Packit Service |
a9274b |
assert(cntr_count > 0);
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
// Detect forgotten to destruct.
|
|
Packit Service |
a9274b |
assert(mapper->private_data == NULL);
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
memset(mapper, 0, sizeof(*mapper));
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
if (type == MAPPER_TYPE_MUXER) {
|
|
Packit Service |
a9274b |
if (cntr_count == 1) {
|
|
Packit Service |
a9274b |
data = &mapper_muxer_single;
|
|
Packit Service |
a9274b |
mapper->target = MAPPER_TARGET_SINGLE;
|
|
Packit Service |
a9274b |
} else {
|
|
Packit Service |
a9274b |
data = &mapper_muxer_multiple;
|
|
Packit Service |
a9274b |
mapper->target = MAPPER_TARGET_MULTIPLE;
|
|
Packit Service |
a9274b |
}
|
|
Packit Service |
a9274b |
} else {
|
|
Packit Service |
a9274b |
if (cntr_count == 1) {
|
|
Packit Service |
a9274b |
data = &mapper_demuxer_single;
|
|
Packit Service |
a9274b |
mapper->target = MAPPER_TARGET_SINGLE;
|
|
Packit Service |
a9274b |
} else {
|
|
Packit Service |
a9274b |
data = &mapper_demuxer_multiple;
|
|
Packit Service |
a9274b |
mapper->target = MAPPER_TARGET_MULTIPLE;
|
|
Packit Service |
a9274b |
}
|
|
Packit Service |
a9274b |
}
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
mapper->ops = &data->ops;
|
|
Packit Service |
a9274b |
mapper->type = type;
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
mapper->private_data = malloc(data->private_size);
|
|
Packit Service |
a9274b |
if (mapper->private_data == NULL)
|
|
Packit Service |
a9274b |
return -ENOMEM;
|
|
Packit Service |
a9274b |
memset(mapper->private_data, 0, data->private_size);
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
mapper->cntr_count = cntr_count;
|
|
Packit Service |
a9274b |
mapper->verbose = verbose;
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
return 0;
|
|
Packit Service |
a9274b |
}
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
int mapper_context_pre_process(struct mapper_context *mapper,
|
|
Packit Service |
a9274b |
snd_pcm_access_t access,
|
|
Packit Service |
a9274b |
unsigned int bytes_per_sample,
|
|
Packit Service |
a9274b |
unsigned int samples_per_frame,
|
|
Packit Service |
a9274b |
unsigned int frames_per_buffer,
|
|
Packit Service |
a9274b |
struct container_context *cntrs)
|
|
Packit Service |
a9274b |
{
|
|
Packit Service |
a9274b |
int err;
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
assert(mapper);
|
|
Packit Service |
a9274b |
assert(access >= SND_PCM_ACCESS_MMAP_INTERLEAVED);
|
|
Packit Service |
a9274b |
assert(access <= SND_PCM_ACCESS_RW_NONINTERLEAVED);
|
|
Packit Service |
a9274b |
assert(bytes_per_sample > 0);
|
|
Packit Service |
a9274b |
assert(samples_per_frame > 0);
|
|
Packit Service |
a9274b |
assert(cntrs);
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
// The purpose of multiple target is to mux/demux each channels to/from
|
|
Packit Service |
a9274b |
// containers.
|
|
Packit Service |
a9274b |
if (mapper->target == MAPPER_TARGET_MULTIPLE &&
|
|
Packit Service |
a9274b |
samples_per_frame != mapper->cntr_count)
|
|
Packit Service |
a9274b |
return -EINVAL;
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
mapper->access = access;
|
|
Packit Service |
a9274b |
mapper->bytes_per_sample = bytes_per_sample;
|
|
Packit Service |
a9274b |
mapper->samples_per_frame = samples_per_frame;
|
|
Packit Service |
a9274b |
mapper->frames_per_buffer = frames_per_buffer;
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
err = mapper->ops->pre_process(mapper, cntrs, mapper->cntr_count);
|
|
Packit Service |
a9274b |
if (err < 0)
|
|
Packit Service |
a9274b |
return err;
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
if (mapper->verbose > 0) {
|
|
Packit Service |
a9274b |
fprintf(stderr, "Mapper: %s\n",
|
|
Packit Service |
a9274b |
mapper_type_labels[mapper->type]);
|
|
Packit Service |
a9274b |
fprintf(stderr, " target: %s\n",
|
|
Packit Service |
a9274b |
mapper_target_labels[mapper->target]);
|
|
Packit Service |
a9274b |
fprintf(stderr, " access: %s\n",
|
|
Packit Service |
a9274b |
snd_pcm_access_name(mapper->access));
|
|
Packit Service |
a9274b |
fprintf(stderr, " bytes/sample: %u\n",
|
|
Packit Service |
a9274b |
mapper->bytes_per_sample);
|
|
Packit Service |
a9274b |
fprintf(stderr, " samples/frame: %u\n",
|
|
Packit Service |
a9274b |
mapper->samples_per_frame);
|
|
Packit Service |
a9274b |
fprintf(stderr, " frames/buffer: %lu\n",
|
|
Packit Service |
a9274b |
mapper->frames_per_buffer);
|
|
Packit Service |
a9274b |
}
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
return 0;
|
|
Packit Service |
a9274b |
}
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
int mapper_context_process_frames(struct mapper_context *mapper,
|
|
Packit Service |
a9274b |
void *frame_buffer,
|
|
Packit Service |
a9274b |
unsigned int *frame_count,
|
|
Packit Service |
a9274b |
struct container_context *cntrs)
|
|
Packit Service |
a9274b |
{
|
|
Packit Service |
a9274b |
assert(mapper);
|
|
Packit Service |
a9274b |
assert(frame_buffer);
|
|
Packit Service |
a9274b |
assert(frame_count);
|
|
Packit Service |
a9274b |
assert(*frame_count <= mapper->frames_per_buffer);
|
|
Packit Service |
a9274b |
assert(cntrs);
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
return mapper->ops->process_frames(mapper, frame_buffer, frame_count,
|
|
Packit Service |
a9274b |
cntrs, mapper->cntr_count);
|
|
Packit Service |
a9274b |
}
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
void mapper_context_post_process(struct mapper_context *mapper)
|
|
Packit Service |
a9274b |
{
|
|
Packit Service |
a9274b |
assert(mapper);
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
if (mapper->ops && mapper->ops->post_process)
|
|
Packit Service |
a9274b |
mapper->ops->post_process(mapper);
|
|
Packit Service |
a9274b |
}
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
void mapper_context_destroy(struct mapper_context *mapper)
|
|
Packit Service |
a9274b |
{
|
|
Packit Service |
a9274b |
assert(mapper);
|
|
Packit Service |
a9274b |
|
|
Packit Service |
a9274b |
if (mapper->private_data)
|
|
Packit Service |
a9274b |
free(mapper->private_data);
|
|
Packit Service |
a9274b |
mapper->private_data = NULL;
|
|
Packit Service |
a9274b |
}
|