xref: /aosp_15_r20/frameworks/av/services/audioflinger/datapath/SpdifStreamOut.h (revision ec779b8e0859a360c3d303172224686826e6e0e1)
1*ec779b8eSAndroid Build Coastguard Worker /*
2*ec779b8eSAndroid Build Coastguard Worker  *
3*ec779b8eSAndroid Build Coastguard Worker  * Copyright 2015, The Android Open Source Project
4*ec779b8eSAndroid Build Coastguard Worker  *
5*ec779b8eSAndroid Build Coastguard Worker  * Licensed under the Apache License, Version 2.0 (the "License");
6*ec779b8eSAndroid Build Coastguard Worker  * you may not use this file except in compliance with the License.
7*ec779b8eSAndroid Build Coastguard Worker  * You may obtain a copy of the License at
8*ec779b8eSAndroid Build Coastguard Worker  *
9*ec779b8eSAndroid Build Coastguard Worker  *     http://www.apache.org/licenses/LICENSE-2.0
10*ec779b8eSAndroid Build Coastguard Worker  *
11*ec779b8eSAndroid Build Coastguard Worker  * Unless required by applicable law or agreed to in writing, software
12*ec779b8eSAndroid Build Coastguard Worker  * distributed under the License is distributed on an "AS IS" BASIS,
13*ec779b8eSAndroid Build Coastguard Worker  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14*ec779b8eSAndroid Build Coastguard Worker  * See the License for the specific language governing permissions and
15*ec779b8eSAndroid Build Coastguard Worker  * limitations under the License.
16*ec779b8eSAndroid Build Coastguard Worker  */
17*ec779b8eSAndroid Build Coastguard Worker 
18*ec779b8eSAndroid Build Coastguard Worker #pragma once
19*ec779b8eSAndroid Build Coastguard Worker 
20*ec779b8eSAndroid Build Coastguard Worker #include <stdint.h>
21*ec779b8eSAndroid Build Coastguard Worker #include <sys/types.h>
22*ec779b8eSAndroid Build Coastguard Worker 
23*ec779b8eSAndroid Build Coastguard Worker #include <system/audio.h>
24*ec779b8eSAndroid Build Coastguard Worker 
25*ec779b8eSAndroid Build Coastguard Worker #include "AudioStreamOut.h"
26*ec779b8eSAndroid Build Coastguard Worker 
27*ec779b8eSAndroid Build Coastguard Worker #include <afutils/NBAIO_Tee.h>
28*ec779b8eSAndroid Build Coastguard Worker #include <audio_utils/spdif/SPDIFEncoder.h>
29*ec779b8eSAndroid Build Coastguard Worker 
30*ec779b8eSAndroid Build Coastguard Worker namespace android {
31*ec779b8eSAndroid Build Coastguard Worker 
32*ec779b8eSAndroid Build Coastguard Worker /**
33*ec779b8eSAndroid Build Coastguard Worker  * Stream that is a PCM data burst in the HAL but looks like an encoded stream
34*ec779b8eSAndroid Build Coastguard Worker  * to the AudioFlinger. Wraps encoded data in an SPDIF wrapper per IEC61973-3.
35*ec779b8eSAndroid Build Coastguard Worker  */
36*ec779b8eSAndroid Build Coastguard Worker class SpdifStreamOut : public AudioStreamOut {
37*ec779b8eSAndroid Build Coastguard Worker public:
38*ec779b8eSAndroid Build Coastguard Worker 
39*ec779b8eSAndroid Build Coastguard Worker     SpdifStreamOut(AudioHwDevice *dev, audio_format_t format);
40*ec779b8eSAndroid Build Coastguard Worker 
41*ec779b8eSAndroid Build Coastguard Worker     status_t open(
42*ec779b8eSAndroid Build Coastguard Worker             audio_io_handle_t handle,
43*ec779b8eSAndroid Build Coastguard Worker             audio_devices_t devices,
44*ec779b8eSAndroid Build Coastguard Worker             struct audio_config *config,
45*ec779b8eSAndroid Build Coastguard Worker             audio_output_flags_t *flags,
46*ec779b8eSAndroid Build Coastguard Worker             const char *address,
47*ec779b8eSAndroid Build Coastguard Worker             const std::vector<playback_track_metadata_v7_t>& sourceMetadata) override;
48*ec779b8eSAndroid Build Coastguard Worker 
49*ec779b8eSAndroid Build Coastguard Worker     /**
50*ec779b8eSAndroid Build Coastguard Worker     * Write audio buffer to driver. Returns number of bytes written, or a
51*ec779b8eSAndroid Build Coastguard Worker     * negative status_t. If at least one frame was written successfully prior to the error,
52*ec779b8eSAndroid Build Coastguard Worker     * it is suggested that the driver return that successful (short) byte count
53*ec779b8eSAndroid Build Coastguard Worker     * and then return an error in the subsequent call.
54*ec779b8eSAndroid Build Coastguard Worker     *
55*ec779b8eSAndroid Build Coastguard Worker     * If set_callback() has previously been called to enable non-blocking mode
56*ec779b8eSAndroid Build Coastguard Worker     * the write() is not allowed to block. It must write only the number of
57*ec779b8eSAndroid Build Coastguard Worker     * bytes that currently fit in the driver/hardware buffer and then return
58*ec779b8eSAndroid Build Coastguard Worker     * this byte count. If this is less than the requested write size the
59*ec779b8eSAndroid Build Coastguard Worker     * callback function must be called when more space is available in the
60*ec779b8eSAndroid Build Coastguard Worker     * driver/hardware buffer.
61*ec779b8eSAndroid Build Coastguard Worker     */
62*ec779b8eSAndroid Build Coastguard Worker     ssize_t write(const void* buffer, size_t bytes) override;
63*ec779b8eSAndroid Build Coastguard Worker 
64*ec779b8eSAndroid Build Coastguard Worker     /**
65*ec779b8eSAndroid Build Coastguard Worker      * @return frame size from the perspective of the application and the AudioFlinger.
66*ec779b8eSAndroid Build Coastguard Worker      */
getFrameSize()67*ec779b8eSAndroid Build Coastguard Worker     [[nodiscard]] size_t getFrameSize() const override { return sizeof(int8_t); }
68*ec779b8eSAndroid Build Coastguard Worker 
69*ec779b8eSAndroid Build Coastguard Worker     /**
70*ec779b8eSAndroid Build Coastguard Worker      * @return audio_config_base_t from the perspective of the application and the AudioFlinger.
71*ec779b8eSAndroid Build Coastguard Worker      */
getAudioProperties()72*ec779b8eSAndroid Build Coastguard Worker     [[nodiscard]] audio_config_base_t getAudioProperties() const override {
73*ec779b8eSAndroid Build Coastguard Worker         return mApplicationConfig;
74*ec779b8eSAndroid Build Coastguard Worker     }
75*ec779b8eSAndroid Build Coastguard Worker 
76*ec779b8eSAndroid Build Coastguard Worker     /**
77*ec779b8eSAndroid Build Coastguard Worker      * @return format from the perspective of the application and the AudioFlinger.
78*ec779b8eSAndroid Build Coastguard Worker      */
getFormat()79*ec779b8eSAndroid Build Coastguard Worker     [[nodiscard]] virtual audio_format_t getFormat() const { return mApplicationConfig.format; }
80*ec779b8eSAndroid Build Coastguard Worker 
81*ec779b8eSAndroid Build Coastguard Worker     /**
82*ec779b8eSAndroid Build Coastguard Worker      * The HAL may be running at a higher sample rate if, for example, playing wrapped EAC3.
83*ec779b8eSAndroid Build Coastguard Worker      * @return sample rate from the perspective of the application and the AudioFlinger.
84*ec779b8eSAndroid Build Coastguard Worker      */
getSampleRate()85*ec779b8eSAndroid Build Coastguard Worker     [[nodiscard]] virtual uint32_t getSampleRate() const { return mApplicationConfig.sample_rate; }
86*ec779b8eSAndroid Build Coastguard Worker 
87*ec779b8eSAndroid Build Coastguard Worker     /**
88*ec779b8eSAndroid Build Coastguard Worker      * The HAL is in stereo mode when playing multi-channel compressed audio over HDMI.
89*ec779b8eSAndroid Build Coastguard Worker      * @return channel mask from the perspective of the application and the AudioFlinger.
90*ec779b8eSAndroid Build Coastguard Worker      */
getChannelMask()91*ec779b8eSAndroid Build Coastguard Worker     [[nodiscard]] virtual audio_channel_mask_t getChannelMask() const {
92*ec779b8eSAndroid Build Coastguard Worker         return mApplicationConfig.channel_mask;
93*ec779b8eSAndroid Build Coastguard Worker     }
94*ec779b8eSAndroid Build Coastguard Worker 
95*ec779b8eSAndroid Build Coastguard Worker     status_t flush() override;
96*ec779b8eSAndroid Build Coastguard Worker     status_t standby() override;
97*ec779b8eSAndroid Build Coastguard Worker 
98*ec779b8eSAndroid Build Coastguard Worker private:
99*ec779b8eSAndroid Build Coastguard Worker 
100*ec779b8eSAndroid Build Coastguard Worker     class MySPDIFEncoder : public SPDIFEncoder
101*ec779b8eSAndroid Build Coastguard Worker     {
102*ec779b8eSAndroid Build Coastguard Worker     public:
MySPDIFEncoder(SpdifStreamOut * spdifStreamOut,audio_format_t format)103*ec779b8eSAndroid Build Coastguard Worker         MySPDIFEncoder(SpdifStreamOut *spdifStreamOut, audio_format_t format)
104*ec779b8eSAndroid Build Coastguard Worker           :  SPDIFEncoder(format)
105*ec779b8eSAndroid Build Coastguard Worker           , mSpdifStreamOut(spdifStreamOut)
106*ec779b8eSAndroid Build Coastguard Worker         {
107*ec779b8eSAndroid Build Coastguard Worker         }
108*ec779b8eSAndroid Build Coastguard Worker 
writeOutput(const void * buffer,size_t bytes)109*ec779b8eSAndroid Build Coastguard Worker         ssize_t writeOutput(const void* buffer, size_t bytes) override
110*ec779b8eSAndroid Build Coastguard Worker         {
111*ec779b8eSAndroid Build Coastguard Worker             return mSpdifStreamOut->writeDataBurst(buffer, bytes);
112*ec779b8eSAndroid Build Coastguard Worker         }
113*ec779b8eSAndroid Build Coastguard Worker     protected:
114*ec779b8eSAndroid Build Coastguard Worker         SpdifStreamOut * const mSpdifStreamOut;
115*ec779b8eSAndroid Build Coastguard Worker     };
116*ec779b8eSAndroid Build Coastguard Worker 
117*ec779b8eSAndroid Build Coastguard Worker     MySPDIFEncoder mSpdifEncoder;
118*ec779b8eSAndroid Build Coastguard Worker     audio_config_base_t mApplicationConfig = AUDIO_CONFIG_BASE_INITIALIZER;
119*ec779b8eSAndroid Build Coastguard Worker 
120*ec779b8eSAndroid Build Coastguard Worker     ssize_t writeDataBurst(const void* data, size_t bytes);
121*ec779b8eSAndroid Build Coastguard Worker 
122*ec779b8eSAndroid Build Coastguard Worker #ifdef TEE_SINK
123*ec779b8eSAndroid Build Coastguard Worker     NBAIO_Tee mTee;
124*ec779b8eSAndroid Build Coastguard Worker #endif
125*ec779b8eSAndroid Build Coastguard Worker 
126*ec779b8eSAndroid Build Coastguard Worker };
127*ec779b8eSAndroid Build Coastguard Worker 
128*ec779b8eSAndroid Build Coastguard Worker } // namespace android
129