Generating RAW (interleaved ECC) from Audio

HI, Guys.

I last posted about 2 years ago and a project from then has come home to roost.

In essence I need to write CD+G discs in raw mode (as all the new drives seem to be loosing cooked mode). I can read a disc in DAO raw mode and write back to it in raw mode. What I need to do now is to take a set of WAV + RW files and create an RAW image prior to burning it.

What I’m looking for are some short cuts. Some source code or similar pointers. I’m reading through my old code and the MMC standards (joy and joy) and have a few bits and bobs from a couple of years ago I don’t quite remember :sad:.

Mostly the stuff I’ve found so far is about decoding to audio rather than encoding from audio.

Any advice or help would be much appreciated.

Iain

Perhaps I’m being over-complicated :o.

From reading my code :confused: and re-reading the MMC standards :frowning: I may just have done most of the work already :). For some reason I had the impression that CD-DA RAW mode also required CRC calculations.

As I now read it, the buffer I need to supply for Raw mode consists of 2352 bytes of plain audio (no messing around with CRC or small frames or stuff) and 96 bytes of CRCd and munged subcodes (which I’ve already got).

So most of the discussions around CRC decoding and such have been related to CD-ROM modes not audio, if I now understand this.

Can you confirm that I’ve got this right (or I suppose tell me I’m wrong!) .

Thanks

Iain

Yup, that is right, CDDA main channel samples are just raw PCM 44.1KHz, stereo 16 bits/sample.

The data format is the same as the plain uncompressed WAVE format (and with the same rates) but with the 44 bytes header stripped, i.e. if you remove the first 44 bytes you have a CDDA track.

For the MMC raw write mode there are 2 modes you can use for CD+G:

[/li]
Write type 3 seems easiest, where the 96 sub-channel data to supply to the writer must be in raw interleaved format, i.e. same form as when you read them from the drive. Sub-channel CRC16 is only for the Q sub-channel bits. There are 2 bytes of Q CRC which covers the first 10 bytes of Q in each sector.

Thanks for your confirmation, Truman.

It seems my work is not quite as simple as I hoped (there’s a shock). I’m writing CD+G to the disc so as well as writing the Q channel and CRC and so on I also need to write the R-W channels with the CRC calculations for both CRC blocks.

There was a thread on this in 2004 entitled [B]CIRC encoding/decoding[/B] which didn’t get quite as far as I’d like.

What I’d mainly like is some code that generated the CRC blocks in the RW Packs. I think I have code which does the interleaving and so on.

Any help would be much appreciated.

Iain

Hehe,

The RW doesn’t contain CRC, it has 2 RS (Reed Solomon) codes (allowing for correction too) which are both defined over GF(2^6) polynomial:

P(X) = X^6 + X + 1

with 1 symbol = 6 bits

with primitive element as:

a = 2

and

P is a (24, 20) RS code
Q is a (4, 2) RS code

Ah, yes of course.

Oddly, that’s just what I read in the standards. Sadly I have almost no idea what it means.

Please, Truman. Don’t make me get my maths books out :sad:

Iain

There is a RS (Reed Solomon) code library that people say works, see post:

http://club.cdfreaks.com/f52/dvd-data-frame-ied-calculation-228652/

The values would be different for n, k for the 2 RS codes:
P: n = 24, k = 20
Q: n = 4, k = 2

Or perhaps cdrtools has the encoding code for CD+G (most likely), and what’s more is that it’s open source, so take a look at:

http://cdrecord.berlios.de/private/cdrecord.html
in the source code in libedc folder these are of interest:
edc_ecc.c
ecc.h
encoder_tables

Hopefully, they would give you the P and Q values which needs to to be added to RW subcodes.

I’m still in the learning phase and only got as far as encoding myself. I’ll be opening my maths book soon again. :slight_smile:

Hmm. It gets ‘more’ interesting.

Where I am is this. I can take a set of source files (audio + RW) write it to the CD in RAW mode (with all the subcode stuff needed) and read it back again in RAW mode.

(thanks for the pointers, cdrtools was the best one)

This works perfectly in the sense that what I get back out of the round trip plays in a karaoke bin file player. In other words, I’ve got back what I put in.

The problem is it won’t play in a karaoke machine (the audio is fine, the graphics are gibberish).

When I look at raw subcodes drawn off a proper karaoke disk, they look entirely different than I was expecting. Broadly, there seems to be the start of a CDG Pack (a graphic command), but then the rest is all garbled (the following byte should be an instruction code. They mainly aren’t).

In other words it looks as if the rw codes have been scrambled.

Now, these same files I get back (from my writing or a real CD) all have good Q codes so my interpretation of the Q bits and packing and unpacking look OK (if the Q codes aren’t largely OK it doesn’t play at all!)

What I’m doing is to copy 96 byte block with the RW codes in into a buffer, work out and apply the P & Q CIRC, then unpack into P-W byte arrays, apply the P and Q streams than repack into a 96 byte block.

Is this how you would expect it to work?

My understanding is that the pack interleaving is handled by the drive. I can’t see how it can be otherwise or the Q subcodes would be so scrambled the disc wouldn’t play at all!

Help!

Iain

Ouch, that is quite confusing.

I think the use of letters being used are to be blamed here.

Hehe, here’s a lecture:

Just a clarification for others also:

Sub-channel bits are defined using letters: P, Q, R, S, T, U, V, W
Some examples of terms used in this case:
Sub P, Sub Q, Subs RW, Sub-channel P, P bits, P sub-code, Q bits, P sub bits

Reed Solomon coding have parities and also commonly uses these letters: P & Q
Some examples of terms used in this case:
P parity, Q parity, P code, P RS code

*Parities are sometimes referred to as codes.

What’s confusing is if you use the word “code”, because the dictionary word code is so generic.

P code <— which one does it refer to? P parity or P subs?

Similarly

Q code <— which one does it refer to? Q parity or Q subs?

Similarly

P sub codes <— which one does it refer to? P parity or P subs?

Anyway, P & Q channel bits in the subchannels doesn’t refer to as Reed Solomon P & Q parities.

[QUOTE=IainDowns;2027686]The problem is it won’t play in a karaoke machine (the audio is fine, the graphics are gibberish).

Now, these same files I get back (from my writing or a real CD) all have good Q codes so my interpretation of the Q bits and packing and unpacking look OK (if the Q codes aren’t largely OK it doesn’t play at all!)
[/QUOTE]Seems it is to do with your generated files output from CD+G mastering software - they forgot to encode (calculate) the P & Q RS parities. In the example files you sent me they are all set to 00s. I guess the hardware player doesn’t like it and stops, while PC software players just keeps playing the graphics.

[QUOTE=IainDowns;2027686]When I look at raw subcodes drawn off a proper karaoke disk, they look entirely different than I was expecting. Broadly, there seems to be the start of a CDG Pack (a graphic command), but then the rest is all garbled (the following byte should be an instruction code. They mainly aren’t).

In other words it looks as if the rw codes have been scrambled.[/QUOTE]If you’ve used the cdrtools (edc_ecc.c) source code then seems there might be a bug, hence funny looking data.

[QUOTE=IainDowns;2027686]What I’m doing is to copy 96 byte block with the RW codes in into a buffer, work out and apply the P & Q RS encoding, then unpack into P-W byte arrays, apply the P and Q streams than repack into a 96 byte block.

Is this how you would expect it to work?[/QUOTE]You wish to take CD+G files output from CD+G mastering software and burn with cdrdao. That tool will accept subs in raw mode, i.e. the RW parts has to be in raw CD+G interleaved format.

So yes, almost:

  1. Take .rw or .cdg mastered files*
  2. Apply P & Q Reed Solomon encoding
  3. Deinterleave bits to apply P & Q sub-channel bits
  4. Interleave bits for cdrdao compliant

*subs with CD+G packed format only - there is no P & Q sub-channel bits

[QUOTE=IainDowns;2027686]My understanding is that the pack interleaving is handled by the drive. I can’t see how it can be otherwise or the Q subcodes would be so scrambled the disc wouldn’t play at all[/QUOTE]You mean the CD+G (RW subs) packed deinterleaving are handled by the drive? If yes, then it depends on the drive and MMC ReadCD sub mode.

And I think you mean Q parities or Q RS codes. :wink:

HI Truman.

I found that the problem was simply that I wasn’t interleaving the R-W. I actually sorted that out some time ago and I meant to post a note to that effect here, but got swamped with other things.

Thanks for your help!

HI, all.

returning to this after some time (writing CD+G disks using DAO raw mode).

It turns out that the code I’ve written is unreliable - that is the resulting disks read correctly on some players and other players they do not. It seems that the more tracks the more likely the disk is to be rejected. ‘Rejected’ either means that the disk cannot be read at all or that the disk loads and plays but the content is somewhat scrambled (audio scratchy and CD+G graphics a mess).

The longer the disk, the worse this is.

I strongly suspect the way I’m writing the TOC, but can’t see what I’m doing wrong.

The thing I’m most confused about is the 150 frames which crops up in this context. This affects the LBA calculation (since the 2s complement numbers seem to start with an offset of 150 - so the maths seems to say).

If this rings any bells or any smart person can explain this 150 frame offset to me, I’d be most grateful…

In my opinion, if the longer the disc the worse the reading, then it isn’t to do with how you have written the data to the disc. More likely it is write speed or disc quality.

Not sure what you mean about the 150 frames… but no data can reside before logical block 0 (ATime 00:02:00), which is 150 frames from the beginning of program area.

RM

Thanks for your response. The problem is affecting all drives and all media I’ve tried so far. And also all speeds, IIRC, though I’m running a test now at 8x (as opposed to full speed) to double check.

I’ve tried adding in the SEND_OPC command which I believe will make the drive do power calibration, but with no difference.

I remain suspicious of the lead in code. What it does is this.

Starts writing at -ATIP Lead in time.
Writes each TOC entry 3 times (with the -ve LBA in Min Sec Frame and the toc details in PMin etc; Although I’ve used 3 copies, I can’t any more find where it says to do that in the MMC. Is this right?).
Continues with this until I get to LBA - 151 (which is written).
From LBA -150 to LBA -1 write blank sectors with LBA in AMin ASec AFrame and the countdown to the start of the program area (2 seconds -> 1 Frame) in the Min Sec Frame.

All of this is done with the P-W CRC’d and interleaved, of course.

NOw I can see nothing which would make this whole thing sensitive to the size of the content on the disk. One test is to record the same data as one track and 12 separate tracks. Both failed to read.

Oh - When I try and read the Toc on these failing discs (with READ TOC (Raw)), I either get an error or I appear to get a truncated TOC.

Any thoughts gratefully received

Iain

I suppose the good news is that my area of suspicion appears to have been right.

All this fuss was apparently due to not bcd encoding the POINT value of the track index in the lead-in. :o

I can’t explain why the problem seemed to crop up around 7 tracks (rather than 9), nor can I explain why this would have caused apparent corruption on the disc at intermediate sizes (around 7 tracks).

I HAVE added SEND_OPC which may have fixed the corruption of course (So there may have been two problems).

For now, it seems to work (pending client testing :slight_smile: of course!), so the forensics are of less interest.

Thanks for all your pointers…

Iain

If I remember correctly, the POINT value in leadin describes the track number being described. If so, then this is certainly a problem if you were using the wrong format (BCD, HEX, etc…). Once you get past track 0x09, the next track would be listed as track 0x0A instead of track 10. It certainly should not have caused any problems before going from track 9 to track 10.

RM