start pcm shenanigains. Still doesn't load

This commit is contained in:
Preston Baxter 2024-07-14 22:41:58 -05:00
parent 33dc918c7a
commit 4f435246d6
1 changed files with 191 additions and 3 deletions

View File

@ -9,6 +9,20 @@
#include <linux/platform_device.h>
#include <sound/pcm.h>
#include <sound/core.h>
#include <sound/initval.h>
static int index[SNDRV_CARDS] = SNDRV_DEFAULT_IDX;
static char *id[SNDRV_CARDS] = SNDRV_DEFAULT_STR;
static bool enable[SNDRV_CARDS] = SNDRV_DEFAULT_ENABLE_PNP;
#define CARD_NAME "AES67 Virtual Soundcard"
module_param_array(index, int, NULL, 0444);
MODULE_PARM_DESC(index, "Index value for " CARD_NAME " soundcard.");
module_param_array(id, charp, NULL, 0444);
MODULE_PARM_DESC(id, "ID string for " CARD_NAME " soundcard.");
module_param_array(enable, bool, NULL, 0444);
MODULE_PARM_DESC(enable, "Enable " CARD_NAME " soundcard.");
MODULE_AUTHOR("Preston Baxter <preston@preston-baxter.xom>");
MODULE_DESCRIPTION("AES67 Virtual Soundcard");
@ -17,11 +31,15 @@ MODULE_LICENSE("GPL");
/* Definistion of AES67 Virtual SoundCard */
struct aes67 {
struct snd_card *card;
struct snd_pcm *pcm;
struct device *dev;
};
/* Destructor */
static int snd_aes67_free(struct aes67 *virtcard)
{
snd_card_free(virtcard->card);
kfree(virtcard);
return 0;
}
@ -74,13 +92,17 @@ static int aes67_probe(struct platform_device *devptr)
int err;
//Incredibly temporary
if (deviceNumber > 1) {
if (deviceNumber >= SNDRV_CARDS) {
return -ENODEV;
}
if (!enable[deviceNumber]) {
deviceNumber++;
return -ENODEV;
}
deviceNumber++;
snd_printk(KERN_INFO "Attempting to create Soundcard for AES67\n");
err = snd_devm_card_new(&devptr->dev, 0, "xid", THIS_MODULE,
err = snd_devm_card_new(&devptr->dev, index[deviceNumber],
id[deviceNumber], THIS_MODULE,
sizeof(struct aes67), &card);
if (err < 0)
snd_printk(KERN_ERR "Unable to create AES67 Soundcard\n");
@ -111,6 +133,172 @@ error:
return err;
}
/* PCM Shenaniagians */
/* Playback definition */
static struct snd_pcm_hardware snd_aes67_playback_hw = {
.info = (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED |
SNDRV_PCM_INFO_BLOCK_TRANSFER | SNDRV_PCM_INFO_MMAP_VALID),
.formats = SNDRV_PCM_FMTBIT_S16_LE,
.rates = SNDRV_PCM_RATE_8000_48000,
.rate_min = 8000,
.rate_max = 48000,
.channels_min = 2,
.channels_max = 2,
.buffer_bytes_max = 32768,
.period_bytes_min = 4096,
.period_bytes_max = 32768,
.periods_min = 1,
.periods_max = 1024,
};
/* Capture definition */
static struct snd_pcm_hardware snd_aes67_capture_hw = {
.info = (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED |
SNDRV_PCM_INFO_BLOCK_TRANSFER | SNDRV_PCM_INFO_MMAP_VALID),
.formats = SNDRV_PCM_FMTBIT_S16_LE,
.rates = SNDRV_PCM_RATE_8000_48000,
.rate_min = 8000,
.rate_max = 48000,
.channels_min = 2,
.channels_max = 2,
.buffer_bytes_max = 32768,
.period_bytes_min = 4096,
.period_bytes_max = 32768,
.periods_min = 1,
.periods_max = 1024,
};
static int snd_aes67_playback_open(struct snd_pcm_substream *substream)
{
struct aes67 *virtcard = snd_pcm_substream_chip(substream);
struct snd_pcm_runtime *runtime = substream->runtime;
runtime->hw = snd_aes67_playback_hw;
return 0;
}
static int snd_aes67_playback_close(struct snd_pcm_substream *substream)
{
struct aes67 *virtcard = snd_pcm_substream_chip(substream);
return 0;
}
static int snd_aes67_capture_open(struct snd_pcm_substream *substream)
{
struct aes67 *virtcard = snd_pcm_substream_chip(substream);
struct snd_pcm_runtime *runtime = substream->runtime;
runtime->hw = snd_aes67_capture_hw;
return 0;
}
static int snd_aes67_capture_close(struct snd_pcm_substream *substream)
{
struct aes67 *virtcard = snd_pcm_substream_chip(substream);
return 0;
}
static int snd_aes67_pcm_hw_params(struct snd_pcm_substream *substream,
struct snd_pcm_hw_params *hw_params)
{
/* the hardware-specific codes will be here */
return 0;
}
/* hw_free callback */
static int snd_aes67_pcm_hw_free(struct snd_pcm_substream *substream)
{
/* the hardware-specific codes will be here */
return 0;
}
static int snd_aes67_pcm_prepare(struct snd_pcm_substream *substream)
{
struct aes67 *chip = snd_pcm_substream_chip(substream);
struct snd_pcm_runtime *runtime = substream->runtime;
/* set up the hardware with the current configuration
* for example...
*/
return 0;
}
static int snd_aes67_pcm_trigger(struct snd_pcm_substream *substream, int cmd)
{
switch (cmd) {
case SNDRV_PCM_TRIGGER_START:
/* do something to start the PCM engine */
break;
case SNDRV_PCM_TRIGGER_STOP:
/* do something to stop the PCM engine */
break;
default:
return -EINVAL;
}
return -EINVAL;
}
static snd_pcm_uframes_t aes67_get_hw_pointer(struct aes67 *virtcard)
{
return 0;
}
static snd_pcm_uframes_t
snd_aes67_pcm_pointer(struct snd_pcm_substream *substream)
{
struct aes67 *chip = snd_pcm_substream_chip(substream);
unsigned int current_frame;
/* get the current hardware pointer */
current_frame = aes67_get_hw_pointer(chip);
return current_frame;
}
/* operators */
static struct snd_pcm_ops snd_aes67_playback_ops = {
.open = snd_aes67_playback_open,
.close = snd_aes67_playback_close,
.hw_params = snd_aes67_pcm_hw_params,
.hw_free = snd_aes67_pcm_hw_free,
.prepare = snd_aes67_pcm_prepare,
.trigger = snd_aes67_pcm_trigger,
.pointer = snd_aes67_pcm_pointer,
};
/* operators */
static struct snd_pcm_ops snd_aes67_capture_ops = {
.open = snd_aes67_capture_open,
.close = snd_aes67_capture_close,
.hw_params = snd_aes67_pcm_hw_params,
.hw_free = snd_aes67_pcm_hw_free,
.prepare = snd_aes67_pcm_prepare,
.trigger = snd_aes67_pcm_trigger,
.pointer = snd_aes67_pcm_pointer,
};
static int snd_aes67_new_pcm(struct aes67 *virtcard)
{
struct snd_pcm *pcm;
int err;
err = snd_pcm_new(virtcard->card, CARD_NAME, 0, 1, 1, &pcm);
if (err < 0)
return err;
pcm->private_data = virtcard;
strcpy(pcm->name, CARD_NAME);
virtcard->pcm = pcm;
/* set operators */
snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK,
&snd_aes67_playback_ops);
snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_CAPTURE, &snd_aes67_capture_ops);
/*Da buffers*/
snd_pcm_set_managed_buffer_all(pcm, SNDRV_DMA_TYPE_DEV, NULL, 64 * 1024,
64 * 1024);
return 0;
}
/* Power Methods */
static int snd_aes67_suspend(struct device *pdev)
{