# DSP Trick: Fast Floating-Point to mu-Law Conversion

From: Jim Thomas Subject: Fast floting point to mu-law conversion Date: 6 May 1999 THIS WORK IS PLACED IN THE PUBLIC DOMAIN

**Name:** Fast floating point to mu-law conversion

**Category:** Algorithmic

**Application:** When you need to convert audio data to mu-law and
don't have a lot of time to mess around.

**Advantages:** Very Fast (I implemented this in a seven cycle loop
on a Sharc processor).

**Introduction:** This trick is based upon the happy coincidence that
mu-law compressed data is very much like a poor man's floating point format.
Mu-law is a companding method fully descried in the ITU specification G.711. I
believe this algorithm to be fully compliant.

**The Trick:** The algorithm is performed in a few steps. The steps
are described below. Although I have implemented and tested this approach in
assembly on a Sharc, I am not at liberty to post the code (I do not own it).
This approach will work when the data is already in floating-point format as
per IEEE 754. Other floating point formats (i.e. Texas Instruments) may work as
well, but will require adaptation. The input data is expected to range from
-1.0 to +1.0. I present a C algorithm, which will not be fast, but should get
the basic idea across.

#define MAX (8031.0/8192.0) #define BIAS (33.0/8192.0) #define MAGIC (0x16f) float x; long mu; long *x_as_long; /* limit the sample between +/- max and take absolute value */ x = input_sample; if ((x < -MAX) || (x > MAX)) x = MAX; else if (x < 0) x = -x; /* add bias */ x += BIAS; /* Extract the segment and quantization bits from the exponent and the mantissa. Since we have limited the range of the signal already, the exponent will be well restricted. The pointer "x_as_long" is used to avoid unwanted type conversion. In assembly, this is easy. */ x_as_long = (long*)&x; mu = (*x_as_long >> 19) & 0xff; /* Unfortunately, mu needs a slight (but magical) adjustment */ mu = MAGIC - mu; /* All that remains is to splice in the sign bit */ if (input_samle >= 0) mu |= 0x80;

- Printer-friendly version
- Login to post comments