This part of the new decoder actually packs the raw DSD
 data into 'DSD-over-USB' format.

---
 src/dsdnative/dsdnative.c |  211
+++++++++++++++++++++++++++++++++++++++++++++
 src/dsdnative/dsdnative.h |   39 ++++++++
 2 files changed, 250 insertions(+), 0 deletions(-)
 create mode 100644 src/dsdnative/dsdnative.c
 create mode 100644 src/dsdnative/dsdnative.h

Jurgen

diff --git a/src/dsdnative/dsdnative.c b/src/dsdnative/dsdnative.c
new file mode 100644
index 0000000..0e5c9ee
--- /dev/null
+++ b/src/dsdnative/dsdnative.c
@@ -0,0 +1,211 @@
+#include <stdlib.h>
+#include <string.h>
+
+#include "dsdnative.h"
+
+/* 09-Dec-11 Jurgen Kramer
+ * dsd2pcm.c converted to output native DSD (packed according to dCS spec) instead of PCM
+ * Tested with Mytek Stereo192-DSD DAC (using Linux snd-dice firewire driver)
+ * 24-bit dCS spec will be put in SAMPLE_FORMAT_S32
+ *
+ * 22-Jan-12 Jurgen Kramer
+ * Add support for DSF (Sony) format
+ */
+
+/* Currently only stereo streams are supported */
+
+/* translate DSF formatted stream to DSD-over-PCM 
+ * 
+ * DSF format uses a interleaved channel format in
+ * 4096 byte blocks
+ *
+ * E.g. for stereo files:
+ * block 1: 4096 bytes left channel data
+ * block 2: 4096 bytes right channel data
+ * block 3: 4096 bytes left channel data
+ * block 4 ...
+ * 
+ * Last blocks are padded with zeros if not completely used
+ *
+ */
+
+extern void dsdnative_translate_dsf(
+	size_t samples,
+	const unsigned char *src, unsigned char *dst, unsigned int dsdsampleformat, uint32_t dsdiff_dsf_bitssample )
+{
+	unsigned char left1, left2, right1, right2;
+	int i;
+	static unsigned char bitreverse[256];
+
+	if ( dsdiff_dsf_bitssample == 1)			/* 1 = LSB first, 8 = MSB first, DSD-over-USB wants MSB first */
+	{
+		int t,e,m;
+		for (t=0, e=0; t<256; ++t)			/* Create bitreverse table */
+		{
+			bitreverse[t] = e;
+			for (m=128; m && !((e^=m)&m); m>>=1)
+				;
+		}
+	}
+
+	/* DSD packed sample format dCS spec (24-bit): 
+	 *	0xAA LSB left --- MSB left  -> 24-bits
+	 *	0xAA LSB Right ---MSB Right -> 24-bits
+	 */
+
+	while ( samples > 0)
+	{
+		/* Process data for the left channel */
+
+		for (i=0; i<2048; i++)
+		{
+			left1 = ( *src ++ );
+			left2 = ( *src ++ );
+	
+			if ( dsdiff_dsf_bitssample == 1)	/* bitreverse needed? */
+			{
+				left1 = bitreverse[left1];
+				left2 = bitreverse[left2];
+			}
+
+			if (dsdsampleformat == 24)
+			{
+				( *dst ++ )= left2;
+				( *dst ++ )= left1;		
+				( *dst ++ )= 0xAA;		/* Must stay here for DAC to lock to DSD! */
+				( *dst ++ )= 0x00;		/* Ignored byte, leave at 0x00 */ 
+			}
+			else
+			{
+				( *dst ++ )= 0x00;		/* Ignored byte, leave at 0x00 */ 
+				( *dst ++ )= left2;
+				( *dst ++ )= left1;		
+				( *dst ++ )= 0xAA;		/* Must stay here for DAC to lock to DSD! */
+			}
+			dst += (ptrdiff_t) 4;
+			samples -= 2;
+		}
+
+		dst -= (ptrdiff_t) 16380;
+	
+		/* Process data for the right channel */
+	
+		for (i=0; i<2048; i++)
+		{
+			right1 = ( *src ++ );
+			right2 = ( *src ++ );
+
+			if ( dsdiff_dsf_bitssample == 1)
+			{
+				right1 = bitreverse[right1];
+				right2 = bitreverse[right2];
+			}
+
+			if (dsdsampleformat == 24)
+			{
+				( *dst ++ )= right2;
+				( *dst ++ )= right1;		
+				( *dst ++ )= 0xAA;		/* Must stay here for DAC to lock to DSD! */
+				( *dst ++ )= 0x00;		/* Ignored byte, leave at 0x00 */ 
+			}
+			else
+			{
+				( *dst ++ )= 0x00;		/* Ignored byte, leave at 0x00 */ 
+				( *dst ++ )= right2;
+				( *dst ++ )= right1;		
+				( *dst ++ )= 0xAA;		/* Must stay here for DAC to lock to DSD! */
+			}	
+			dst += (ptrdiff_t) 4;
+			samples -= 2;
+		}
+		dst -= (ptrdiff_t) 4;
+	}
+}
+
+/* translate DFF formatted stream to DSD-over-PCM */
+
+extern void dsdnative_translate_dff(
+	size_t samples,
+	const unsigned char *src, unsigned char *dst, unsigned int dsdsampleformat )
+{
+	unsigned char left1, left2, right1, right2;
+
+	/* DSD packed sample format dCS spec (24-bit): 
+	 *	0xAA LSB left --- MSB left  -> 24-bits
+	 *	0xAA LSB Right ---MSB Right -> 24-bits
+	 */
+
+	while (samples > 0)
+	{
+		if (samples == 2)				/* Process last two samples */
+		{
+			left1 = ( *src ++ );
+			right1 = ( *src ++ );
+
+			if (dsdsampleformat == 24)
+			{
+				/* This 'works' for SAMPLE_FORMAT_S24_P32 when converted back to SAMPLE_FORMAT_S32 by mpd */
+				( *dst ++ )= 0x00;
+				( *dst ++ )= left1;		
+				( *dst ++ )= 0xAA;		/* Must stay here for DAC to lock to DSD! */
+				( *dst ++ )= 0x00;		/* Ignored byte, leave at 0x00 */ 
+
+				( *dst ++ )= 0x00;
+				( *dst ++ )= right1;
+				( *dst ++ )= 0xAA;		/* Must stay here for DAC to lock to DSD! */
+				( *dst ++ )= 0x00;		/* Ignored byte, leave at 0x00 */ 
+			}
+			else
+			{
+				( *dst ++ )= 0x00;		/* Ignored byte, leave at 0x00 */ 
+				( *dst ++ )= 0x00;		/* Last 2 samples: no left2 sample */
+				( *dst ++ )= left1;		
+				( *dst ++ )= 0xAA;		/* Must stay here for DAC to lock to DSD! */
+	
+				( *dst ++ )= 0x00;		/* Ignored byte, leave at 0x00 */
+				( *dst ++ )= 0x00;		/* Last 2 samples: no right2 sample */
+				( *dst ++ )= right1;
+				( *dst ++ )= 0xAA;		/* Must stay here for DAC to lock to DSD! */
+			}
+			samples = 0;
+
+		}
+		else
+		{
+			left1 = ( *src ++ );
+			right1 = ( *src ++ );
+			left2 = ( *src ++ );
+			right2 = ( *src ++ );
+		
+			if (dsdsampleformat == 24)
+			{
+			/* This 'works' for SAMPLE_FORMAT_S24_P32 when convert back to SAMPLE_FORMAT_S32 by mpd */
+
+				( *dst ++ )= left2;
+				( *dst ++ )= left1;		
+				( *dst ++ )= 0xAA;		/* Must stay here for DAC to lock to DSD! */
+				( *dst ++ )= 0x00;		/* Ignored byte, leave at 0x00 */ 
+
+				( *dst ++ )= right2;
+				( *dst ++ )= right1;
+				( *dst ++ )= 0xAA;		/* Must stay here for DAC to lock to DSD! */
+				( *dst ++ )= 0x00;		/* Ignored byte, leave at 0x00 */ 
+			}
+			else
+			{
+				( *dst ++ )= 0x00;		/* Ignored byte, leave at 0x00 */ 
+				( *dst ++ )= left2;
+				( *dst ++ )= left1;		
+				( *dst ++ )= 0xAA;		/* Must stay here for DAC to lock to DSD! */
+	
+				( *dst ++ )= 0x00;		/* Ignore byte, leave at 0x00 */
+				( *dst ++ )= right2;
+				( *dst ++ )= right1;
+				( *dst ++ )= 0xAA;		/* Must stay here for DAC to lock to DSD! */
+			}	
+			samples = samples - 4;
+		}
+	}
+
+}
+
diff --git a/src/dsdnative/dsdnative.h b/src/dsdnative/dsdnative.h
new file mode 100644
index 0000000..1aa4ab5
--- /dev/null
+++ b/src/dsdnative/dsdnative.h
@@ -0,0 +1,39 @@
+#ifndef DSDNATIVE_H_INCLUDED
+#define DSDNATIVE_H_INCLUDED
+
+#include <stddef.h>
+#include <string.h>
+
+#include <stdint.h>			/* for uint32_t */
+
+/**
+ * "translates" a stream of octets to a stream 
+ * of packed DSD formatted pcm
+ * 
+ * @param samples -- number of octets/samples to "translate"
+ * @param src -- pointer to first octet (input)
+ * @param dst -- pointer to first sample(output) 
+ * @param dsdsampleformat -- 32 or 24-bit output sample format
+ * Version for handling DFF (Philips) format
+ */
+extern void dsdnative_translate_dff(size_t samples,
+	const unsigned char *src, unsigned char *dst, unsigned int dsdsampleformat );
+
+/**
+ * "translates" a stream of octets to a stream 
+ * of packed DSD formatted pcm
+ * 
+ * @param samples -- number of octets/samples to "translate"
+ * @param src -- pointer to first octet (input)
+ * @param dst -- pointer to first 32-bits sample(output)
+ * @param dsdsampleformat -- 32 or 24-bit output sample format 
+ * @param dsdiff_dsf_bitssample -- 1 = LSB, 8 = MSB
+ *
+ * Version for handling DSF (Sony) format
+ */
+
+extern void dsdnative_translate_dsf(size_t samples,
+	const unsigned char *src, unsigned char *dst, unsigned int dsdsampleformat, uint32_t dsdiff_dsf_bitssample );
+
+#endif /* include guard DSDNATIVE_H_INCLUDED */
+
-- 
1.7.6.5

------------------------------------------------------------------------------
Try before you buy = See our experts in action!
The most comprehensive online learning library for Microsoft developers
is just $99.99! Visual Studio, SharePoint, SQL - plus HTML5, CSS3, MVC3,
Metro Style Apps, more. Free future releases when you subscribe now!
http://p.sf.net/sfu/learndevnow-dev2
_______________________________________________
Musicpd-dev-team mailing list
Musicpd-dev-team@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/musicpd-dev-team

Reply via email to