/* * Copyright (c) 2026 Abdelkader Boudih * * SPDX-License-Identifier: BSD-2-Clause */ #ifndef _DEV_FIREWIRE_FWISOUND_H_ #define _DEV_FIREWIRE_FWISOUND_H_ #include /* Protocol reverse-engineered by Clemens Ladisch (Linux isight-firmware). */ #define FWISOUND_SPEC_ID APPLE_FW_OUI #define FWISOUND_VERSION 0x000010 /* SW_ISIGHT_AUDIO */ #define APPLE_FW_OUI 0x000a27 /* Audio register offsets from audio_base */ #define FWISOUND_REG_AUDIO_ENABLE 0x000 /* bit31 = enable streaming */ #define FWISOUND_REG_DEF_AUDIO_GAIN 0x204 #define FWISOUND_REG_GAIN_RAW_START 0x210 #define FWISOUND_REG_GAIN_RAW_END 0x214 #define FWISOUND_REG_GAIN_DB_START 0x218 #define FWISOUND_REG_GAIN_DB_END 0x21c #define FWISOUND_REG_SAMPLE_RATE_INQ 0x280 #define FWISOUND_REG_ISO_TX_CONFIG 0x300 /* bits[19:16]=speed, [3:0]=ch*/ #define FWISOUND_REG_SAMPLE_RATE 0x400 /* bit31 = 1 → 48000 Hz */ #define FWISOUND_REG_GAIN 0x500 #define FWISOUND_REG_MUTE 0x504 /* REG_AUDIO_ENABLE / REG_SAMPLE_RATE bit */ #define FWISOUND_AUDIO_ENABLE (1u << 31) #define FWISOUND_RATE_48000 (1u << 31) /* Apple FireWire audio ISO payload. */ struct fwisound_payload { uint32_t sample_count; /* samples in this packet */ uint32_t signature; /* 0x73676874 = "sght" */ uint32_t sample_total; /* running total (drop detect)*/ uint32_t reserved; int16_t samples[2 * 475]; /* stereo S16BE; *2 valid */ }; #define FWISOUND_SIGNATURE 0x73676874u /* "sght" */ /* ISO DMA parameters */ #define FWISOUND_ISO_CHANNEL 1 #define FWISOUND_ISO_NCHUNK 64 #define FWISOUND_ISO_PKTSIZE 2048 /* MCLBYTES */ /* Driver states */ #define FWISOUND_STATE_IDLE 0 #define FWISOUND_STATE_PROBED 1 #define FWISOUND_STATE_STREAMING 2 #define FWISOUND_STATE_DETACHING 3 #ifdef _KERNEL #include struct fwisound_chan { struct fwisound_softc *sc; struct pcm_channel *pcm_chan; struct snd_dbuf *buf; struct pcmchan_caps caps; uint32_t fmts[2]; uint32_t hw_ptr; /* ring write offset (bytes) */ int running; }; struct fwisound_softc { struct firewire_dev_comm fd; /* MUST BE FIRST */ struct mtx mtx; device_t dev; device_t pcm_dev; struct fw_device *fwdev; uint16_t cmd_hi; /* always 0xffff */ uint32_t cmd_lo; /* 0xf0000000|(audio_base<<2) */ struct task probe_task; struct task start_task; /* deferred iso_start */ struct task stop_task; /* deferred iso_stop */ /* ISO streaming */ int dma_ch; /* -1 = not open */ int iso_active; /* iso_input running */ uint8_t iso_channel; /* PCM channel back-reference */ struct fwisound_chan *chan; /* Sample drop detection */ uint32_t sample_total; /* Gain range (read from camera during probe) */ int32_t gain_raw_min; int32_t gain_raw_max; int state; int dropped; }; #define FWISOUND_LOCK(sc) mtx_lock(&(sc)->mtx) #define FWISOUND_UNLOCK(sc) mtx_unlock(&(sc)->mtx) int fwisound_iso_start(struct fwisound_softc *); void fwisound_iso_stop(struct fwisound_softc *); #endif /* _KERNEL */ #endif /* _DEV_FIREWIRE_FWISOUND_H_ */