mirror of
				https://github.com/PabloMK7/citra.git
				synced 2025-10-31 05:40:04 +00:00 
			
		
		
		
	audio_core: hle: mf: make DetectMediaType return a struct
This commit is contained in:
		
							parent
							
								
									168f2ee79a
								
							
						
					
					
						commit
						ab1f47ed15
					
				
					 3 changed files with 23 additions and 16 deletions
				
			
		|  | @ -163,7 +163,7 @@ std::optional<BinaryResponse> WMFDecoder::Impl::Decode(const BinaryRequest& requ | |||
| 
 | ||||
|     if (!initalized) { | ||||
|         LOG_DEBUG(Audio_DSP, "Decoder not initalized"); | ||||
|         // This is a hack to continue games that are not compiled with the aac codec
 | ||||
|         // This is a hack to continue games when decoder failed to initialize
 | ||||
|         return response; | ||||
|     } | ||||
| 
 | ||||
|  | @ -176,21 +176,21 @@ std::optional<BinaryResponse> WMFDecoder::Impl::Decode(const BinaryRequest& requ | |||
| 
 | ||||
|     std::array<std::vector<u8>, 2> out_streams; | ||||
|     unique_mfptr<IMFSample> sample; | ||||
|     ADTSData adts_header; | ||||
|     char* aac_tag = (char*)calloc(1, 14); | ||||
|     MFInputState input_status = MFInputState::OK; | ||||
|     std::optional<ADTSMeta> adts_meta = DetectMediaType((char*)data, request.size); | ||||
| 
 | ||||
|     if (DetectMediaType((char*)data, request.size, &adts_header, &aac_tag) != 0) { | ||||
|     if (!adts_meta) { | ||||
|         LOG_ERROR(Audio_DSP, "Unable to deduce decoding parameters from ADTS stream"); | ||||
|         return response; | ||||
|     } | ||||
| 
 | ||||
|     response.num_channels = adts_header.channels; | ||||
|     response.num_channels = adts_meta->ADTSHeader.channels; | ||||
| 
 | ||||
|     if (!selected) { | ||||
|         LOG_DEBUG(Audio_DSP, "New ADTS stream: channels = {}, sample rate = {}", | ||||
|                   adts_header.channels, adts_header.samplerate); | ||||
|         SelectInputMediaType(transform.get(), in_stream_id, adts_header, (UINT8*)aac_tag, 14); | ||||
|                   adts_meta->ADTSHeader.channels, adts_meta->ADTSHeader.samplerate); | ||||
|         SelectInputMediaType(transform.get(), in_stream_id, adts_meta->ADTSHeader, | ||||
|                              adts_meta->AACTag, 14); | ||||
|         SelectOutputMediaType(transform.get(), out_stream_id); | ||||
|         SendSample(transform.get(), in_stream_id, nullptr); | ||||
|         // cache the result from detect_mediatype and call select_*_mediatype only once
 | ||||
|  | @ -205,7 +205,7 @@ std::optional<BinaryResponse> WMFDecoder::Impl::Decode(const BinaryRequest& requ | |||
|     while (true) { | ||||
|         input_status = SendSample(transform.get(), in_stream_id, sample.get()); | ||||
| 
 | ||||
|         if (DecodingLoop(adts_header, out_streams) == MFOutputState::FatalError) { | ||||
|         if (DecodingLoop(adts_meta->ADTSHeader, out_streams) == MFOutputState::FatalError) { | ||||
|             // if the decode issues are caused by MFT not accepting new samples, try again
 | ||||
|             // NOTICE: you are required to check the output even if you already knew/guessed
 | ||||
|             // MFT didn't accept the input sample
 | ||||
|  |  | |||
|  | @ -209,17 +209,18 @@ bool SelectOutputMediaType(IMFTransform* transform, int out_stream_id, GUID audi | |||
|     return false; | ||||
| } | ||||
| 
 | ||||
| int DetectMediaType(char* buffer, size_t len, ADTSData* output, char** aac_tag) { | ||||
| std::optional<ADTSMeta> DetectMediaType(char* buffer, size_t len) { | ||||
|     if (len < 7) { | ||||
|         return -1; | ||||
|         return std::nullopt; | ||||
|     } | ||||
| 
 | ||||
|     ADTSData tmp; | ||||
|     ADTSMeta result; | ||||
|     // see https://docs.microsoft.com/en-us/windows/desktop/api/mmreg/ns-mmreg-heaacwaveinfo_tag
 | ||||
|     // for the meaning of the byte array below
 | ||||
| 
 | ||||
|     // it might be a good idea to wrap the parameters into a struct
 | ||||
|     // and pass that struct into the function but this will lead to messier code
 | ||||
|     // and pass that struct into the function but doing that will lead to messier code
 | ||||
|     // const UINT8 aac_data[] = { 0x01, 0x00, 0xfe, 00, 00, 00, 00, 00, 00, 00, 00, 00, 0x11, 0x90
 | ||||
|     // }; first byte: 0: raw aac 1: adts 2: adif 3: latm/laos
 | ||||
|     UINT8 aac_tmp[] = {0x01, 0x00, 0xfe, 00, 00, 00, 00, 00, 00, 00, 00, 00, 0x00, 0x00}; | ||||
|  | @ -227,15 +228,15 @@ int DetectMediaType(char* buffer, size_t len, ADTSData* output, char** aac_tag) | |||
| 
 | ||||
|     tmp = ParseADTS(buffer); | ||||
|     if (tmp.length == 0) { | ||||
|         return -1; | ||||
|         return std::nullopt; | ||||
|     } | ||||
| 
 | ||||
|     tag = MFGetAACTag(tmp); | ||||
|     aac_tmp[12] |= (tag & 0xff00) >> 8; | ||||
|     aac_tmp[13] |= (tag & 0x00ff); | ||||
|     std::memcpy(*aac_tag, aac_tmp, 14); | ||||
|     std::memcpy(output, &tmp, sizeof(ADTSData)); | ||||
|     return 0; | ||||
|     std::memcpy(&(result.ADTSHeader), &tmp, sizeof(ADTSData)); | ||||
|     std::memcpy(&(result.AACTag), aac_tmp, 14); | ||||
|     return result; | ||||
| } | ||||
| 
 | ||||
| void MFFlush(IMFTransform* transform) { | ||||
|  |  | |||
|  | @ -58,6 +58,12 @@ auto Amp(SmartPtr& smart_ptr) { | |||
| // convient function for formatting error messages
 | ||||
| void ReportError(std::string msg, HRESULT hr); | ||||
| 
 | ||||
| // data type for transferring ADTS metadata between functions
 | ||||
| struct ADTSMeta { | ||||
|     ADTSData ADTSHeader; | ||||
|     u8 AACTag[14]; | ||||
| }; | ||||
| 
 | ||||
| // exported functions
 | ||||
| bool MFCoInit(); | ||||
| unique_mfptr<IMFTransform> MFDecoderInit(GUID audio_format = MFAudioFormat_AAC); | ||||
|  | @ -67,7 +73,7 @@ unique_mfptr<IMFSample> CreateSample(void* data, DWORD len, DWORD alignment = 1, | |||
| bool SelectInputMediaType(IMFTransform* transform, int in_stream_id, const ADTSData& adts, | ||||
|                           UINT8* user_data, UINT32 user_data_len, | ||||
|                           GUID audio_format = MFAudioFormat_AAC); | ||||
| int DetectMediaType(char* buffer, size_t len, ADTSData* output, char** aac_tag); | ||||
| std::optional<ADTSMeta> DetectMediaType(char* buffer, size_t len); | ||||
| bool SelectOutputMediaType(IMFTransform* transform, int out_stream_id, | ||||
|                            GUID audio_format = MFAudioFormat_PCM); | ||||
| void MFFlush(IMFTransform* transform); | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue