1 /*
2  * Copyright (C) 2024 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 package com.android.car.audio;
17 
18 import static android.media.FadeManagerConfiguration.FADE_STATE_DISABLED;
19 
20 import static com.android.car.internal.ExcludeFromCodeCoverageGeneratedReport.DUMP_INFO;
21 
22 import android.annotation.Nullable;
23 import android.car.oem.CarAudioFadeConfiguration;
24 import android.media.AudioAttributes;
25 import android.media.FadeManagerConfiguration;
26 import android.media.VolumeShaper;
27 import android.util.proto.ProtoOutputStream;
28 
29 import com.android.car.audio.CarAudioDumpProto.CarAudioAttributesProto;
30 import com.android.car.audio.CarAudioDumpProto.CarAudioFadeConfigurationProto;
31 import com.android.car.internal.ExcludeFromCodeCoverageGeneratedReport;
32 
33 import java.util.List;
34 
35 /**
36  * Utils for common proto dump functionalities
37  */
38 @ExcludeFromCodeCoverageGeneratedReport(reason = DUMP_INFO)
39 /* package */ final class CarAudioProtoUtils {
40 
CarAudioProtoUtils()41     private CarAudioProtoUtils() {
42     }
43 
dumpCarAudioAttributesListProto(@ullable List<AudioAttributes> attributesList, long fieldId, ProtoOutputStream proto)44     static void dumpCarAudioAttributesListProto(@Nullable List<AudioAttributes> attributesList,
45             long fieldId, ProtoOutputStream proto) {
46         if (attributesList == null) {
47             return;
48         }
49 
50         for (int index = 0; index < attributesList.size(); index++) {
51             dumpCarAudioAttributesProto(attributesList.get(index), fieldId, proto);
52         }
53     }
54 
dumpCarAudioAttributesProto(@ullable AudioAttributes attributes, long fieldId, ProtoOutputStream proto)55     static void dumpCarAudioAttributesProto(@Nullable AudioAttributes attributes, long fieldId,
56             ProtoOutputStream proto) {
57         if (attributes == null) {
58             return;
59         }
60 
61         long token = proto.start(fieldId);
62         proto.write(CarAudioAttributesProto.USAGE, attributes.getUsage());
63         proto.write(CarAudioAttributesProto.CONTENT_TYPE, attributes.getContentType());
64         proto.end(token);
65     }
66 
dumpCarAudioFadeConfigurationProto( @ullable CarAudioFadeConfiguration carAudioFadeConfiguration, long fieldId, ProtoOutputStream proto)67     static void dumpCarAudioFadeConfigurationProto(
68             @Nullable CarAudioFadeConfiguration carAudioFadeConfiguration,
69             long fieldId, ProtoOutputStream proto) {
70         if (carAudioFadeConfiguration == null) {
71             return;
72         }
73 
74         long token = proto.start(fieldId);
75         proto.write(CarAudioFadeConfigurationProto.NAME, carAudioFadeConfiguration.getName());
76         dumpFadeManagerConfigurationProto(carAudioFadeConfiguration.getFadeManagerConfiguration(),
77                 CarAudioFadeConfigurationProto.FADE_MANAGER_CONFIGURATION, proto);
78         proto.end(token);
79     }
80 
dumpFadeManagerConfigurationProto( @ullable FadeManagerConfiguration fadeManagerConfig, long fieldId, ProtoOutputStream proto)81     private static void dumpFadeManagerConfigurationProto(
82             @Nullable FadeManagerConfiguration fadeManagerConfig, long fieldId,
83             ProtoOutputStream proto) {
84         if (fadeManagerConfig == null) {
85             return;
86         }
87 
88         long token = proto.start(fieldId);
89         int fadeState = fadeManagerConfig.getFadeState();
90         proto.write(CarAudioFadeConfigurationProto.FadeManagerConfigurationProto.STATE,
91                 fadeManagerConfig.getFadeState());
92         if (fadeState == FADE_STATE_DISABLED) {
93             proto.end(token);
94             return;
95         }
96 
97         List<Integer> fadeableUsages = fadeManagerConfig.getFadeableUsages();
98 
99         dumpIntegerListForRepeatedProto(fadeableUsages,
100                 CarAudioFadeConfigurationProto.FadeManagerConfigurationProto.FADEABLE_USAGES,
101                 proto);
102         dumpIntegerListForRepeatedProto(fadeManagerConfig.getUnfadeableContentTypes(),
103                 CarAudioFadeConfigurationProto.FadeManagerConfigurationProto
104                         .UNFADEABLE_CONTENT_TYPES, proto);
105         dumpIntegerListForRepeatedProto(fadeManagerConfig.getUnfadeableUids(),
106                 CarAudioFadeConfigurationProto.FadeManagerConfigurationProto.UNFADEABLE_UIDS,
107                 proto);
108         dumpCarAudioAttributesListProto(fadeManagerConfig.getUnfadeableAudioAttributes(),
109                 CarAudioFadeConfigurationProto.FadeManagerConfigurationProto.UNFADEABLE_ATTRIBUTES,
110                 proto);
111 
112         for (int index = 0; index < fadeableUsages.size(); index++) {
113             int usage = fadeableUsages.get(index);
114             dumpUsageToVolumeShaperConfigProto(usage,
115                     fadeManagerConfig.getFadeOutVolumeShaperConfigForUsage(usage),
116                     CarAudioFadeConfigurationProto.FadeManagerConfigurationProto
117                             .USAGES_TO_VOLUME_SHAPER_CONFIG,
118                     CarAudioFadeConfigurationProto.FadeManagerConfigurationProto
119                             .UsagesToVolumeShaperConfiguration.FADE_OUT_VOL_SHAPER_CONFIG, proto);
120             dumpUsageToVolumeShaperConfigProto(usage,
121                     fadeManagerConfig.getFadeInVolumeShaperConfigForUsage(usage),
122                     CarAudioFadeConfigurationProto.FadeManagerConfigurationProto
123                             .USAGES_TO_VOLUME_SHAPER_CONFIG,
124                     CarAudioFadeConfigurationProto.FadeManagerConfigurationProto
125                             .UsagesToVolumeShaperConfiguration.FADE_IN_VOL_SHAPER_CONFIG, proto);
126         }
127 
128         List<AudioAttributes> attrsWithVolumeShapers = fadeManagerConfig
129                 .getAudioAttributesWithVolumeShaperConfigs();
130         for (int index = 0; index < attrsWithVolumeShapers.size(); index++) {
131             AudioAttributes attr = attrsWithVolumeShapers.get(index);
132             dumpAttributeToVolumeShaperConfigProto(attr,
133                     fadeManagerConfig.getFadeOutVolumeShaperConfigForAudioAttributes(attr),
134                     CarAudioFadeConfigurationProto.FadeManagerConfigurationProto
135                             .ATTR_TO_VOLUME_SHAPER_CONFIG,
136                     CarAudioFadeConfigurationProto.FadeManagerConfigurationProto
137                             .AttributeToVolumeShaperConfiguration.FADE_OUT_VOL_SHAPER_CONFIG,
138                     proto);
139             dumpAttributeToVolumeShaperConfigProto(attr,
140                     fadeManagerConfig.getFadeInVolumeShaperConfigForAudioAttributes(attr),
141                     CarAudioFadeConfigurationProto.FadeManagerConfigurationProto
142                             .ATTR_TO_VOLUME_SHAPER_CONFIG,
143                     CarAudioFadeConfigurationProto.FadeManagerConfigurationProto
144                             .AttributeToVolumeShaperConfiguration.FADE_IN_VOL_SHAPER_CONFIG, proto);
145         }
146         proto.end(token);
147     }
148 
dumpIntegerListForRepeatedProto(List<Integer> integerList, long repeatedFieldId, ProtoOutputStream proto)149     private static void dumpIntegerListForRepeatedProto(List<Integer> integerList,
150             long repeatedFieldId, ProtoOutputStream proto) {
151         for (int index = 0; index < integerList.size(); index++) {
152             proto.write(repeatedFieldId, integerList.get(index));
153         }
154     }
155 
dumpUsageToVolumeShaperConfigProto(int usage, @Nullable VolumeShaper.Configuration volShaperConfig, long fieldId, long fadeTypeFieldId, ProtoOutputStream proto)156     private static void dumpUsageToVolumeShaperConfigProto(int usage,
157             @Nullable VolumeShaper.Configuration volShaperConfig, long fieldId,
158             long fadeTypeFieldId, ProtoOutputStream proto) {
159         if (volShaperConfig == null) {
160             return;
161         }
162 
163         long token = proto.start(fieldId);
164         proto.write(CarAudioFadeConfigurationProto.FadeManagerConfigurationProto
165                 .UsagesToVolumeShaperConfiguration.USAGE, usage);
166         dumpVolumeShaperConfiguration(volShaperConfig, fadeTypeFieldId, proto);
167         proto.end(token);
168     }
169 
dumpAttributeToVolumeShaperConfigProto(@ullable AudioAttributes attr, @Nullable VolumeShaper.Configuration volShaperConfig, long fieldId, long fadeTypeFieldId, ProtoOutputStream proto)170     private static void dumpAttributeToVolumeShaperConfigProto(@Nullable AudioAttributes attr,
171             @Nullable VolumeShaper.Configuration volShaperConfig, long fieldId,
172             long fadeTypeFieldId, ProtoOutputStream proto) {
173         if (volShaperConfig == null || attr == null) {
174             return;
175         }
176 
177         long token = proto.start(fieldId);
178         dumpCarAudioAttributesProto(attr, CarAudioFadeConfigurationProto
179                 .FadeManagerConfigurationProto.AttributeToVolumeShaperConfiguration.ATTRIBUTES,
180                 proto);
181         dumpVolumeShaperConfiguration(volShaperConfig, fadeTypeFieldId, proto);
182         proto.end(token);
183     }
184 
dumpVolumeShaperConfiguration(VolumeShaper.Configuration volShaperConfig, long fieldId, ProtoOutputStream proto)185     private static void dumpVolumeShaperConfiguration(VolumeShaper.Configuration volShaperConfig,
186             long fieldId, ProtoOutputStream proto) {
187         long token = proto.start(fieldId);
188         proto.write(CarAudioFadeConfigurationProto.FadeManagerConfigurationProto
189                 .VolumeShaperConfiguration.DURATION, volShaperConfig.getDuration());
190         proto.end(token);
191     }
192 }
193