// Detect It Easy: detection rule file
// Authors: Levis <levintaeyeon@live.com>
//         Jason Hood <jadoxa@yahoo.com.au>
//         Kaens (TG @kaens)
// ref. official RIFF WAVE format doc; vgmstream > riff.c, msadpcm_decoder.c

meta("audio", "RIFF container/WAVE file (.WAV)");

/* beautify ignore:start */
function detect() {

	const debug = 0;

	var
		p = 0xC, e = _BE,
		labl = [], txts = [],
		dcsamples = cue = 0,
		nFormat = nRate = nChannels = nBPS = 0,
		dur = -1, sz = -1,
		lp = 0,
		fmtsz = 0, datasz = 0,
		hksz = 4,
		hkhd = "", title = "", dt = "", by = "", genre = "", cms = "", cmt = "", cop = "", sft = "",
		end = false, checklist = [false, false, false];
	if (X.Sz() < 36) return;
	if(X.c("'RIFF'........'WAVE'")) e = _LE;
	else if(X.c("'RIFX'........'WAVE'")) e = _BE;
	else return;
	if((sz = 8+X.U32(4, e)) < 12) return;
	function msadpcm_check_coefs(o) { //returns new offset or -1 for a failed check
		const coefs = [ [256,0], [512,-256], [0,0], [ 192,64], [240, 0], [460,-208], [392,-232] ];
		var c = X.U16(o, e); if(c != 7) return -1;  o += 2;
		for(var i=0; i < 7; i++,o+=4) {
			var c1 = X.I16(o, e), c2 = X.I16(o + 2, e);
			if (c1 != coefs[i][0] || c2 != coefs[i][1]) return -1;
		}
		return o
	}
	if(sz-8 >= X.Sz() && X.c("'NXBF'",0x24)) sz = X.Sz();
	if(debug) var chunks = "";
	while (p < X.Sz() && p < sz) {
		hkhd = X.SA(p, 4);
		hksz = X.U32(p + 4, e);
		if(debug) chunks += " " + hkhd + " [" + Hex(hksz) + "] @" + Hex(p);
		p += 8;
		switch (hkhd) {
			case "fmt ": checklist[0] = true; fmtsz = hksz;
				nFormat = X.U16(p, e);
				nChannels = X.U16(p + 2, e);
				nRate = X.U32(p + 4, e);
				nBlockSize = X.U16(p + 0xC, e);
				nBPS = X.U16(p + 0x0E, e);
				switch (nFormat) {
				case 0x0000: sVersion = "Yamaha AICA ADPCM (unofficial)";
					if(sz-4 == X.Sz()) sz -= 4; else if(sz-8 == X.Sz()) sz -= 8; else if(sz+2 == X.Sz()) sz -= 2;
					if(hksz == 0x12) hksz += 2;
					break;
				case 0x0001: if((nBPS & 7) || !isWithin(nBPS, 8,32)) return;  sVersion = "Microsoft PCM"
					+ (nBPS == 32? "32_le": nBPS == 24? "24_le": nBPS == 16? "16":"8U") +" (uncompressed)";
					break;
				case 0x0002:
					if(nBPS == 4) { if(msadpcm_check_coefs(p+0x14) < 0) { if(debug)_l2r('wav',2,'coefs are off'); return } }
					else if(nBPS == 16 && nBlockSize == 2*nChannels && sz >= 0x14-8) sVersion = "MS-IMA ADPCM";
					else sVersion = "Microsoft ADPCM";
					break;
				case 0x0003: if(nBPS != 32) return;  sVersion = "Microsoft IEEE float"; break;
				case 0x0004: sVersion = "Compaq VSELP"; break;
				case 0x0005: sVersion = "IBM CVSD"; break;
				case 0x0006: sVersion = "ITU G.711 a-law"; break;
				case 0x0007: sVersion = "ITU G.711 u-law"; break;
				case 0x0008: sVersion = "Microsoft DTS"; break;
				case 0x0009: sVersion = "DRM"; break;
				case 0x000A: sVersion = "WMA 9 Speech"; break;
				case 0x000B: sVersion = "Microsoft Windows Media RT Voice"; break;
				case 0x0010: sVersion = "OKI-ADPCM"; break;
				case 0x0011: if(nBPS == 4) sVersion = "MS-IMA ADPCM"; else sVersion = "Intel IMA/DVI-ADPCM";
					if((sz-8) >> 2 == X.U32(0x30, e)) sz = X.Sz();
					else if(X.Sz()-sz-0x10 <= 0x900 && X.c("'cont'",sz)) sz += 8+X.U32(sz+4, e);
					break;
				case 0x0012: sVersion = "Videologic Mediaspace ADPCM"; break;
				case 0x0013: sVersion = "Sierra ADPCM"; break;
				case 0x0014: sVersion = "Antex G.723 ADPCM"; break;
				case 0x0015: sVersion = "DSP Solutions DIGISTD"; break;
				case 0x0016: sVersion = "DSP Solutions DIGIFIX"; break;
				case 0x0017: sVersion = "Dialogic OKI ADPCM"; break;
				case 0x0018: sVersion = "Media Vision ADPCM"; break;
				case 0x0019: sVersion = "HP CU"; break;
				case 0x001A: sVersion = "HP Dynamic Voice"; break;
				case 0x0020: if(nBPS == 4) sVersion = "Yamaha AICA ADPCM"; else sVersion = "Yamaha ADPCM"; break;
				case 0x0021: sVersion = "SONARC Speech Compression"; break;
				case 0x0022: sVersion = "DSP Group True Speech"; break;
				case 0x0023: sVersion = "Echo Speech Corp."; break;
				case 0x0024: sVersion = "Virtual Music Audiofile AF36"; break;
				case 0x0025: sVersion = "Audio Processing Tech."; break;
				case 0x0026: sVersion = "Virtual Music Audiofile AF10"; break;
				case 0x0027: sVersion = "Aculab Prosody 1612"; break;
				case 0x0028: sVersion = "Merging Tech. LRC"; break;
				case 0x0030: sVersion = "Dolby AC2"; break;
				case 0x0031: sVersion = "Microsoft GSM610"; break;
				case 0x0032: sVersion = "MSN Audio"; break;
				case 0x0033: sVersion = "Antex ADPCM"; break;
				case 0x0034: sVersion = "Control Resources VQLPC"; break;
				case 0x0035: sVersion = "DSP Solutions DIGIREAL"; break;
				case 0x0036: sVersion = "DSP Solutions DIGIADPCM"; break;
				case 0x0037: sVersion = "Control Resources CR10"; break;
				case 0x0038: sVersion = "Natural MicroSystems VBX ADPCM"; break;
				case 0x0039: sVersion = "Crystal Semiconductors IMA ADPCM"; break;
				case 0x003A: sVersion = "Echo Speech ECHOSC3"; break;
				case 0x003B: sVersion = "Rockwell ADPCM"; break;
				case 0x003C: sVersion = "Rockwell DIGITALK"; break;
				case 0x003D: sVersion = "Xebec Multimedia"; break;
				case 0x0040: sVersion = "Antex G.721 ADPCM"; break;
				case 0x0041: sVersion = "Antex G.728 CELP"; break;
				case 0x0042: sVersion = "Microsoft MSG723"; break;
				case 0x0043: sVersion = "IBM AVC ADPCM"; break;
				case 0x0045: sVersion = "ITU-T G.726"; break;
				case 0x0050: sVersion = "Microsoft MPEG"; break;
				case 0x0051: sVersion = "RT23 or PAC"; break;
				case 0x0052: sVersion = "InSoft RT24"; break;
				case 0x0053: sVersion = "InSoft PAC"; break;
				case 0x0055: sVersion = "MP3"; break;
				case 0x0059: sVersion = "Cirrus"; break;
				case 0x0060: sVersion = "Cirrus Logic"; break;
				case 0x0061: sVersion = "ESS Tech. PCM"; break;
				case 0x0062: sVersion = "Voxware Inc."; break;
				case 0x0063: sVersion = "Canopus ATRAC"; break;
				case 0x0064: sVersion = "APICOM G.726 ADPCM"; break;
				case 0x0065: sVersion = "APICOM G.722 ADPCM"; break;
				case 0x0066: sVersion = "Microsoft DSAT"; break;
				case 0x0067: sVersion = "Microsoft DSAT-DISPLAY"; break;
				case 0x0069: if(nBPS == 4) sVersion = "XBOX IMA ADPCM"; else sVersion = "Voxware Byte Aligned";
					if(sz-8 == X.Sz()) sz -= 8; else if(sz-4 == X.Sz()) sz -= 4; else if(sz+8 == X.Sz()) sz += 8;
					break;
				case 0x0070: sVersion = "Voxware ACB"; break;
				case 0x0071: sVersion = "Voxware AC10"; break;
				case 0x0072: sVersion = "Voxware AC16"; break;
				case 0x0073: sVersion = "Voxware AC20"; break;
				case 0x0074: sVersion = "Voxware MetaVoice"; break;
				case 0x0075: sVersion = "Voxware MetaSound"; break;
				case 0x0076: sVersion = "Voxware RT29HW"; break;
				case 0x0077: sVersion = "Voxware VR12"; break;
				case 0x0078: sVersion = "Voxware VR18"; break;
				case 0x0079: sVersion = "Voxware TQ40"; break;
				case 0x007A:
					if(extIs('med')) {
						if(nBPS == 4) sVersion = "4-bit MS-IMA ADPCM";
						else if(nBPS == 3) sVersion = "3-bit MS-IMA ADPCM";
						else sVersion = "Voxware SC3/med"
					} else sVersion = "Voxware SC3"; break;
				case 0x007B: sVersion = "Voxware SC3"; break;
				case 0x0080: sVersion = "Soundsoft"; break;
				case 0x0081: sVersion = "Voxware TQ60"; break;
				case 0x0082: sVersion = "Microsoft MSRT24"; break;
				case 0x0083: sVersion = "AT&T G.729A"; break;
				case 0x0084: sVersion = "Motion Pixels MVI-MV12"; break;
				case 0x0085: sVersion = "DataFusion G.726"; break;
				case 0x0086: sVersion = "DataFusion GSM610"; break;
				case 0x0088: sVersion = "Iterated Systems Audio"; break;
				case 0x0089: sVersion = "Onlive"; break;
				case 0x008A: sVersion = "Multitude, Inc. FT SX20"; break;
				case 0x008B: sVersion = "Infocom IT’S A/S G.721 ADPCM"; break;
				case 0x008C: sVersion = "Convedia G729"; break;
				case 0x008D: sVersion = "Congruency, Inc. (not specified)"; break;
				case 0x0091: sVersion = "Siemens SBC24"; break;
				case 0x0092: sVersion = "Sonic Foundry Dolby AC3 APDIF"; break;
				case 0x0093: sVersion = "MediaSonic G.723"; break;
				case 0x0094: sVersion = "Aculab Prosody 8kbps"; break;
				case 0x0097: sVersion = "ZyXEL ADPCM"; break;
				case 0x0098: sVersion = "Philips LPCBB"; break;
				case 0x0099: sVersion = "Studer Professional Audio Packed"; break;
				case 0x00A0: sVersion = "Maiden PhonyTalk"; break;
				case 0x00A1: sVersion = "Racal Recorder GSM"; break;
				case 0x00A2: sVersion = "Racal Recorder G720.a"; break;
				case 0x00A3: sVersion = "Racal G723.1"; break;
				case 0x00A4: sVersion = "Racal Tetra ACELP"; break;
				case 0x00B0: sVersion = "NEC AAC NEC Corporation"; break;
				case 0x00FF: sVersion = "AAC"; break;
				case 0x0100: sVersion = "Rhetorex ADPCM"; break;
				case 0x0101: sVersion = "IBM u-Law"; break;
				case 0x0102: sVersion = "IBM a-Law"; break;
				case 0x0103: sVersion = "IBM ADPCM"; break;
				case 0x0111: sVersion = "Vivo G.723"; break;
				case 0x0112: sVersion = "Vivo Siren"; break;
				case 0x0120: sVersion = "Philips Speech Processing CELP"; break;
				case 0x0121: sVersion = "Philips Speech Processing GRUNDIG"; break;
				case 0x0123: sVersion = "Digital G.723"; break;
				case 0x0125: sVersion = "Sanyo LD ADPCM"; break;
				case 0x0130: sVersion = "Sipro Lab ACEPLNET"; break;
				case 0x0131: sVersion = "Sipro Lab ACELP4800"; break;
				case 0x0132: sVersion = "Sipro Lab ACELP8V3"; break;
				case 0x0133: sVersion = "Sipro Lab G.729"; break;
				case 0x0134: sVersion = "Sipro Lab G.729A"; break;
				case 0x0135: sVersion = "Sipro Lab Kelvin"; break;
				case 0x0136: sVersion = "VoiceAge AMR"; break;
				case 0x0140: sVersion = "Dictaphone G.726 ADPCM"; break;
				case 0x0150: sVersion = "Qualcomm PureVoice"; break;
				case 0x0151: sVersion = "Qualcomm HalfRate"; break;
				case 0x0155: sVersion = "Ring Zero Systems TUBGSM"; break;
				case 0x0160: sVersion = "Microsoft Audio1"; break;
				case 0x0161: sVersion = "Windows Media Audio V2 V7 V8 V9 / DivX audio (WMA) / Alex AC3 Audio"; break;
				case 0x0162: sVersion = "Windows Media Audio Professional V9"; break;
				case 0x0163: sVersion = "Windows Media Audio Lossless V9"; break;
				case 0x0164: sVersion = "WMA Pro over S/PDIF"; break;
				case 0x0170: sVersion = "UNISYS NAP ADPCM"; break;
				case 0x0171: sVersion = "UNISYS NAP ULAW"; break;
				case 0x0172: sVersion = "UNISYS NAP ALAW"; break;
				case 0x0173: sVersion = "UNISYS NAP 16K"; break;
				case 0x0174: sVersion = "MM SYCOM ACM SYC008 SyCom Technologies"; break;
				case 0x0175: sVersion = "MM SYCOM ACM SYC701 G726L SyCom Technologies"; break;
				case 0x0176: sVersion = "MM SYCOM ACM SYC701 CELP54 SyCom Technologies"; break;
				case 0x0177: sVersion = "MM SYCOM ACM SYC701 CELP68 SyCom Technologies"; break;
				case 0x0178: sVersion = "Knowledge Adventure ADPCM"; break;
				case 0x0180: sVersion = "Fraunhofer IIS MPEG2AAC"; break;
				case 0x0190: sVersion = "Digital Theater Systems DTS DS"; break;
				case 0x0200: sVersion = "Creative Labs ADPCM"; break;
				case 0x0202: sVersion = "Creative Labs FASTSPEECH8"; break;
				case 0x0203: sVersion = "Creative Labs FASTSPEECH10"; break;
				case 0x0210: sVersion = "UHER ADPCM"; break;
				case 0x0215: sVersion = "Ulead DV ACM"; break;
				case 0x0216: sVersion = "Ulead DV ACM"; break;
				case 0x0220: sVersion = "Quarterdeck Corp."; break;
				case 0x0230: sVersion = "I-Link VC"; break;
				case 0x0240: sVersion = "Aureal Semiconductor Raw Sport"; break;
				case 0x0241: sVersion = "ESST AC3"; break;
				case 0x0250: sVersion = "Interactive Products HSX"; break;
				case 0x0251: sVersion = "Interactive Products RPELP"; break;
				case 0x0260: sVersion = "Consistent CS2"; break;
				case 0x0270: sVersion = "ATRAC3/Sony SCX"; break;
				case 0x0271: sVersion = "Sony SCY"; break;
				case 0x0272: sVersion = "Sony ATRAC3"; break;
				case 0x0273: sVersion = "Sony SPC"; break;
				case 0x0280: sVersion = "TELUM Telum Inc."; break;
				case 0x0281: sVersion = "TELUMIA Telum Inc."; break;
				case 0x0285: sVersion = "Norcom Voice Systems ADPCM"; break;
				case 0x0300:
					if(sz-8 == X.Sz()) sz -= 8;
					if(nBPS == 4 && nBlockSize == 0x400*nChannels && sz == 0x14-8 && nChannels == 1) sVersion = "DVI IMA";
					else sVersion = "Fujitsu FM TOWNS SND";
					break;
				case 0x0301: sVersion = "Fujitsu (not specified)"; break;
				case 0x0302: sVersion = "Fujitsu (not specified)"; break;
				case 0x0303: sVersion = "Fujitsu (not specified)"; break;
				case 0x0304: sVersion = "Fujitsu (not specified)"; break;
				case 0x0305: sVersion = "Fujitsu (not specified)"; break;
				case 0x0306: sVersion = "Fujitsu (not specified)"; break;
				case 0x0307: sVersion = "Fujitsu (not specified)"; break;
				case 0x0308: sVersion = "Fujitsu (not specified)"; break;
				case 0x0350: sVersion = "Micronas Semiconductors, Inc. Development"; break;
				case 0x0351: sVersion = "Micronas Semiconductors, Inc. CELP833"; break;
				case 0x0400: sVersion = "Brooktree Digital"; break;
				case 0x0401: sVersion = "Intel Music Coder (IMC)"; break;
				case 0x0402: sVersion = "Ligos Indeo Audio"; break;
				case 0x0450: sVersion = "QDesign Music"; break;
				case 0x0500: sVersion = "On2 VP7 On2 Technologies"; break;
				case 0x0501: sVersion = "On2 VP6 On2 Technologies"; break;
				case 0x0555: sVersion = "Level-5 4-bit ADPCM"; //unofficial
					var fsz = sz+4*(X.U16(0x16, e)-1); if (fsz < X.Sz() && X.Sz() - fsz < 0x10) sz = fsz;
					break;
				case 0x0680: sVersion = "AT&T VME VMPCM"; break;
				case 0x0681: sVersion = "AT&T TCP"; break;
				case 0x0700: sVersion = "YMPEG Alpha (dummy for MPEG-2 compressor)"; break;
				case 0x08AE: sVersion = "ClearJump LiteWave (lossless)"; break;
				case 0x1000: sVersion = "Olivetti GSM"; break;
				case 0x1001: sVersion = "Olivetti ADPCM"; break;
				case 0x1002: sVersion = "Olivetti CELP"; break;
				case 0x1003: sVersion = "Olivetti SBC"; break;
				case 0x1004: sVersion = "Olivetti OPR"; break;
				case 0x1100: sVersion = "Lernout & Hauspie"; break;
				case 0x1101: sVersion = "Lernout & Hauspie CELP"; break;
				case 0x1102: sVersion = "Lernout & Hauspie SBC"; break;
				case 0x1103: sVersion = "Lernout & Hauspie SBC"; break;
				case 0x1104: sVersion = "Lernout & Hauspie SBC"; break;
				case 0x1400: sVersion = "Norris Comm. Inc."; break;
				case 0x1401: sVersion = "ISIAudio"; break;
				case 0x1500: sVersion = "AT&T Soundspace Music Compression"; break;
				case 0x181C: sVersion = "VoxWare RT24 speech"; break;
				case 0x181E: sVersion = "Lucent elemedia AX24000P Music"; break;
				case 0x1971: sVersion = "Sonic Foundry LOSSLESS"; break;
				case 0x1979: sVersion = "Innings Telecom Inc. ADPCM"; break;
				case 0x1C07: sVersion = "Lucent SX8300P speech"; break;
				case 0x1C0C: sVersion = "Lucent SX5363S G.723 compliant"; break;
				case 0x1F03: sVersion = "CUseeMe DigiTalk (ex-Rocwell)"; break;
				case 0x1FC4: sVersion = "NCT Soft ALF2CD ACM"; break;
				case 0x2000: sVersion = "FAST Multimedia DVM"; break;
				case 0x2001: sVersion = "Dolby DTS"; break;
				case 0x2002: sVersion = "RealAudio 1 / 2 14.4"; break;
				case 0x2003: sVersion = "RealAudio 1 / 2 28.8"; break;
				case 0x2004: sVersion = "RealAudio G2 / 8 Cook (low bitrate)"; break;
				case 0x2005: sVersion = "RealAudio 3 / 4 / 5 Music (DNET)"; break;
				case 0x2006: sVersion = "RealAudio 10 AAC (RAAC)"; break;
				case 0x2007: sVersion = "RealAudio 10 AAC+ (RACP)"; break;
				case 0x2500: sVersion = "Reserved range to 0x2600 Microsoft"; break;
				case 0x3313: sVersion = "makeAVIS (ffvfw fake AVI sound from AviSynth scripts)"; break;
				case 0x4143: sVersion = "Divio MPEG-4 AAC audio"; break;
				case 0x4201: sVersion = "Nokia adaptive multirate"; break;
				case 0x4243: sVersion = "Divio G726 Divio, Inc."; break;
				case 0x434C: sVersion = "LEAD Speech"; break;
				case 0x564C: sVersion = "LEAD Vorbis"; break;
				case 0x5756: sVersion = "WavPack Audio"; break;
				case 0x674F: sVersion = "Ogg Vorbis (mode 1)"; break;
				case 0x6750: sVersion = "Ogg Vorbis (mode 2)"; break;
				case 0x6751: sVersion = "Ogg Vorbis (mode 3)"; break;
				case 0x676F: sVersion = "Ogg Vorbis (mode 1+)"; break;
				case 0x6770: sVersion = "Ogg Vorbis (mode 2+)"; break;
				case 0x6771: sVersion = "Ogg Vorbis (mode 3+)"; break;
				case 0x7000: sVersion = "3COM NBX 3Com Corporation"; break;
				case 0x706D: sVersion = "FAAD AAC"; break;
				case 0x7A21: sVersion = "GSM-AMR (CBR, no SID)"; break;
				case 0x7A22: sVersion = "GSM-AMR (VBR, including SID)"; break;
				case 0xA100: sVersion = "Comverse Infosys Ltd. G723 1"; break;
				case 0xA101: sVersion = "Comverse Infosys Ltd. AVQSBC"; break;
				case 0xA102: sVersion = "Comverse Infosys Ltd. OLDSBC"; break;
				case 0xA103: sVersion = "Symbol Technologies G729A"; break;
				case 0xA104: sVersion = "VoiceAge AMR WB VoiceAge Corporation"; break;
				case 0xA105: sVersion = "Ingenient Technologies Inc. G726"; break;
				case 0xA106: sVersion = "ISO/MPEG-4 advanced audio Coding"; break;
				case 0xA107: sVersion = "Encore Software Ltd G726"; break;
				case 0xA109: sVersion = "Speex ACM Codec xiph.org"; break;
				case 0xDFAC: sVersion = "DebugMode SonicFoundry Vegas FrameServer ACM"; break;
				case 0xF1AC: sVersion = "Free Lossless Audio Codec FLAC"; break;
				case 0xFFFE: sVersion = "Extensible";
					var guid1 = X.U32(0x20, _LE), guid2 = (X.U16(0x24, _LE) << 16) | X.U16(0x26, _LE),
						guid3 = X.U32(0x28,_BE), guid4 = X.U32(0x2C,_BE);
					if(guid1 == 1 && guid2 == 0x10 && guid3 == 0x800000AA && guid4 == 0x00389B71)
						if(nBPS == 16) sVersion += ":PCM16";
					if(guid1 == 0xE923AABF && guid2 == 0xCB584471 && guid3 == 0xA119FFFA && guid4 == 0x01E4CE62)
						sVersion += ":ATRAC3+";
					if(guid1 == 0x47E142D2 && guid2 == 0x36BA4D8D && guid3 == 0x88FC6165 && guid4 == 0x4F8C836C)
						sVersion += ":ATRAC9";
					if(sz +0x18 == X.Sz()) sz += 0x18;
					else if(sz+0x38 == X.Sz()) sz += 0x38;
					else if(sz+0x40 == X.Sz()) sz -= 0x40;
					break;
				case 0xFFFF: sVersion = "Development"; break;
				default: sVersion = "Unknown:"+Hex(nFormat,4)
				}
				break;

			case "fact": dcsamples = X.U32(p, _LE); break; //the uncompressed (factual?) file size?

			case "data": checklist[1] = true; datasz = hksz;
				if (nBPS && nFormat == 1 && !(nBPS % 8)) {
					var nmSeconds = Math.round(X.U32(p - 4, e) / (nBPS >> 3) / nRate / nChannels * 10000) / 10;
					dur = new Date(nmSeconds).toISOString().substr(11, 8);
				}
				break;

			case "cue":
				var q = p + 4,
					hhd = "", hsz = 0;
				while (q < p + hksz && q < X.Sz()) {
					hhd = X.SA(q, 4);
					hsz = X.U32(q+4, _LE);
					q += 8;
					if(hhd == 'data') cue++;
					q += hsz + hsz & 1;
				}
				break;

			case "cmnt":
				cmt = cmt.appendS(X.SC(p+2,hksz-8,'SJIS'),'\n'); //gamerip stuff, so Japanese
				break;

			case "LIST": case "list": // lowercase non-standard but there are such files...
				if(["INFO","ADTL"].includes(X.SA(p,4).toUpperCase())) {
					var q = p + 4,
						hhd = "", hsz = 0;
					while (q < p + hksz && q < X.Sz()) {
						hhd = X.SA(q, 4);
						hsz = X.U32(q+4, _LE);
						q += 8;
						switch (hhd) {
							case "INAM": title = X.SC(q,hsz,'CP1252'); break;
							case "IART": by = X.SC(q,hsz,'CP1252'); break;
							case "ICMS": cms = X.SC(q,hsz,'CP1252'); break;
							case "ICOP": cop = X.SC(q,hsz,'CP1252'); break;
							case "ICRD": dt = X.SC(q,hsz,'CP1252'); break;
							case "ISFT": sft = X.SC(q,hsz,'CP1252'); break;
							case "IGNR": genre = X.SC(q,hsz,'CP1252'); break;
							case "ICMT": cmt = cmt.appendS(X.SC(q,hsz,'CP1252'),'\n'); break;
							case "labl": labl.push(X.SC(q+4,hsz-4,'CP1252').trim()); break;
							case "ltxt": txts.push(X.SC(q+0x14,hsz-0x14, X.SA(q+0x12,2)).trim()); break;
						}
						hsz += hsz & 1;
						q += hsz
					}
				}
				break;
			case "smpl": lp = X.U32(p+0x1C, e); break;
			case "wsmp": lp = X.U32(p+0x10, e); break;
			case "ctrl": lp = (X.I32(p, e) ? 1 : 0); break;
			case "NXBF": hksz = X.U32(p, e); p += 4; ch += '/'+X.U32(p+0xC, e); lp = X.I32(0x10, e) >= 0 ? 1 : 0; break;
			case "JUNK": checklist[2] = true; break
		}
		hksz += hksz & 1; //align
		p += hksz
	} // end of chunks

	if(!checklist[0] || !checklist[1]) return;  bDetected = true;
	sVersion += e == _LE? "/le": "/be";
	fact = Math.round(dcsamples / 0x100000);

	function is_ue4_msadpcm() {
		if(!extIs('adpcm')) return; //TODO tighten it enough that it can tell em apart
		function is_ue4_blocks() {
			var maxj = Math.min(10*nBlockSize, datasz);
			for(j=0; j < maxj; j += nBlockSize) {
				var coefs = X.U8(j), scale = X.U16(j+1, _LE);
				if(coefs > 7) return; 
				if(nBlockSize == 0x200) { if(scale == 0x00E6 && coefs != 0) return }
				else if(scale > 0x4000) return
			}
			return true
		}
		if(nChannels < 2 || fact > 0) return;
		if(fmtsz == 0x36 && nBlockSize != 0x200) return;
		if(fmtsz == 0x32 && ![0x200,0x9B,0x69].includes(nBlockSize)) return;
		return true
	}
	if(nFormat == 2 && nBPS == 4 && is_ue4_msadpcm()) sVersion = sVersion.appendS('UE4','/');

	if((nFormat & 0xFF00) == 0x6700 && sz+1 == X.Sz()) sz += 1;

	if (debug) if (chunks != "") _l2r('riff-wave',0,'chunks: ['+chunks+']');

	if(X.isVerbose()) {
		sOptionT(addEllipsis(title)); sOptionT(dt, 'created: '); sOptionT(addEllipsis(by),'by: ');
		sOptionT(genre, 'genre: '); sOptionT(addEllipsis(sft), 's/w: '); sOptionT(addEllipsis(cms), 'cms.by: ');
		sOptionT(cop, '©'); sOption(addEllipsis(cmt.trim()),'cmt: "', '"');
		if(labl.length) sOptionT(addEllipsis(labl.filter(function(x){return x.length>0}).join('; ')),'labels: "', '"');
		if(txts.length) sOptionT(addEllipsis(txts.filter(function(x){return x.length>0}).join('; ')),'captions: "', '"');
		sOption('ch:' + nChannels + (nBPS ? ' ' + nBPS + '-bit' : '') + ' s/r:' + nRate + 'Hz'
			+ (dcsamples ? ' fact:' + fact + 'M' : '') //for compressed things only
			+ (dur !== -1 ? ' len: '+dur : '')
			+ (lp > 0 ? ' looped'+(lp>1?'×'+lp:'') : '')
			+' sz:'+outSz(sz));
	}

	return result();
}
/* beautify ignore:end */