Skip to content

Commit

Permalink
gsm-receiver: EFR support [2/3] Add unmapping support to OpenBTS TCH …
Browse files Browse the repository at this point in the history
…decoder

Signed-off-by: Sylvain Munaut <[email protected]>
  • Loading branch information
smunaut authored and laf0rge committed Oct 30, 2010
1 parent a9619b0 commit ef32a06
Show file tree
Hide file tree
Showing 3 changed files with 78 additions and 26 deletions.
66 changes: 41 additions & 25 deletions gsm-receiver/src/lib/decoder/openbtsstuff/GSML1FEC.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,8 @@
//#include "GSMConfig.h"
#include "GSMTDMA.h"
#include "GSM610Tables.h"
#include "GSM660Tables.h"
#include "GSM690Tables.h"
#include "Assert.h"


Expand Down Expand Up @@ -78,7 +80,7 @@ using namespace GSM;
TCHFACCHL1Decoder::TCHFACCHL1Decoder(const TDMAMapping& wMapping)
: mTCHU(189), mTCHD(260), mC(456),
mClass1_c(mC.head(378)), mClass1A_d(mTCHD.head(50)), mClass2_c(mC.segment(378, 78)),
mTCHParity(0x0b, 3, 50), mMapping(wMapping)
mTCHParity(0x0b, 3, 50), mMapping(wMapping), mMode(MODE_SPEECH_FR)
{
for (int i = 0; i < 8; i++) {
mI[i] = SoftVector(114);
Expand Down Expand Up @@ -186,10 +188,6 @@ bool TCHFACCHL1Decoder::decodeTCH(bool stolen)
// If the frame wasn't stolen, we'll update this with parity later.
bool good = !stolen;

// Good or bad, we will be sending *something* to the speech channel.
// Allocate it in this scope.
unsigned char * newFrame = new unsigned char[33];

if (!stolen) {

// 3.1.2.2
Expand Down Expand Up @@ -226,29 +224,47 @@ bool TCHFACCHL1Decoder::decodeTCH(bool stolen)
<< " calcParity=" << calcParity << " tail=" << tail);
good = (sentParity == calcParity) && (tail == 0);
if (good) {
// Undo Um's importance-sorted bit ordering.
// See GSM 05.03 3.1 and Tablee 2.
BitVector payload = mVFrame.payload();
mTCHD.unmap(g610BitOrder, 260, payload);
mVFrame.pack(newFrame);
// Save a copy for bad frame processing.
memcpy(mPrevGoodFrame, newFrame, 33);
return true;
}
}
if (mMode == MODE_SPEECH_FR) {
// Undo Um's importance-sorted bit ordering.
// See GSM 05.03 3.1 and Tablee 2.
BitVector payload = mVFrame.payload();
mTCHD.unmap(g610BitOrder, 260, payload);
mVFrame.pack(mPrevGoodFrame);
mPrevGoodFrameLength = 33;
} else if (mMode == MODE_SPEECH_EFR) {
BitVector payload = mVFrameAMR.payload();
BitVector TCHW(260), EFRBits(244);

if (!good) {
// TODO -- Bad frame processing, GSM 06.11.
// For now, just repeat the last good frame.
// TODO -- Need to apply attenuation and randomization of grid positions.
memcpy(newFrame, mPrevGoodFrame, 33);
//d_gsm_file.write((char *)newFrame, 33);
}
// Undo Um's EFR bit ordering.
mTCHD.unmap(g660BitOrder, 260, TCHW);

// Remove repeating bits and CRC to get raw EFR frame (244 bits)
for (unsigned k=0; k<71; k++)
EFRBits[k] = TCHW[k] & 1;

for (unsigned k=73; k<123; k++)
EFRBits[k-2] = TCHW[k] & 1;


// Good or bad, we must feed the speech channel.
// mSpeechQ.write(newFrame);
for (unsigned k=125; k<178; k++)
EFRBits[k-4] = TCHW[k] & 1;

for (unsigned k=180; k<230; k++)
EFRBits[k-6] = TCHW[k] & 1;

for (unsigned k=232; k<252; k++)
EFRBits[k-8] = TCHW[k] & 1;

// Map bits as AMR 12.2k
EFRBits.map(g690_12_2_BitOrder, 244, payload);

// Put the whole frame (hdr + payload)
mVFrameAMR.pack(mPrevGoodFrame);
mPrevGoodFrameLength = 32;
}

return true;
}
}

return false;
}
Expand Down
20 changes: 19 additions & 1 deletion gsm-receiver/src/lib/decoder/openbtsstuff/GSML1FEC.h
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,10 @@ namespace GSM
*/


enum TCHMode {
MODE_SPEECH_FR,
MODE_SPEECH_EFR,
};


/** L1 decoder used for full rate TCH and FACCH -- mostly from GSM 05.03 3.1 and 4.2 */
Expand All @@ -75,8 +79,10 @@ namespace GSM
SoftVector mClass2_c; ///< the class 2 part of c[]
ViterbiR2O4 mVCoder;

VocoderFrame mVFrame; ///< unpacking buffer for vocoder frame
VocoderFrame mVFrame; ///< buffer for FR vocoder frame
VocoderAMRFrame mVFrameAMR; ///< buffer for EFR vocoder frame packed in AMR container
unsigned char mPrevGoodFrame[33]; ///< previous good frame.
unsigned int mPrevGoodFrameLength;

Parity mTCHParity;
const TDMAMapping& mMapping; ///< multiplexing description
Expand All @@ -85,6 +91,7 @@ namespace GSM

static const unsigned mMaxQSize = 3;

enum TCHMode mMode;

public:

Expand All @@ -94,6 +101,14 @@ namespace GSM
return FACCHType;
}

enum TCHMode mode() const {
return mMode;
}

void setMode(enum TCHMode mode) {
mMode = mode;
}


/** TCH/FACCH has a special-case writeLowSide. */
void writeLowSide(const RxBurst& inBurst);
Expand All @@ -118,6 +133,9 @@ namespace GSM
unsigned char * get_voice_frame(){
return mPrevGoodFrame;
}
unsigned int get_voice_frame_length(){
return mPrevGoodFrameLength;
}
/**
Receive a traffic frame.
Non-blocking. Returns NULL if queue is dry.
Expand Down
18 changes: 18 additions & 0 deletions gsm-receiver/src/lib/decoder/openbtsstuff/VocoderFrame.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,4 +22,22 @@ class VocoderFrame : public BitVector {

};

class VocoderAMRFrame : public BitVector {

public:

VocoderAMRFrame()
:BitVector(244+8)
{ fillField(0,0x3c,8); /* AMR-NB 12.2 */ }

/** Construct by unpacking a char[32]. */
VocoderAMRFrame(const unsigned char *src)
:BitVector(244+8)
{ unpack(src); }

BitVector payload() { return tail(8); }
const BitVector payload() const { return tail(8); }

};

#endif

0 comments on commit ef32a06

Please sign in to comment.