The DSP microprocessor is a 16bit integer processor with some
extra support for fractional arithmetic.
Fractional arithmetic turns out to be very useful for DSP
programming, since it frees us from worries about overflow on
multiplies. (Two 16bit numbers, multiplied together, can
require 32 bits for the result. Two 16bit fixedpoint
fractional numbers also require 32 bits for the result, but
the 32bit result can be rounded into 16 bits while only
introducing an error of approximately
216
2
16
.) For this reason, we will be using fixedpoint
fractional representation to describe filter taps and inputs
throughout this course.
Unfortunately, the assembler and debugger we are using do not
recognize this fractional fixedpoint representation. For this
reason, when you are using the assembler or debugger, you will
see decimal values (ranging from 32768 to 32767) on screen
instead of the fraction being represented. The conversion is
simple; the fractional number being represented is simply the
decimal value shown divided by 32768. This allows us to
represent numbers between 1 and
1−215
1
2
15
.
1 cannot be represented exactly.
When we multiply using this representation,
an extra shift left is required. Consider the two examples
below:
Table 2
fractional 
0.5×0.5=0.25
0.5
0.5
0.25

decimal 
16384×16384=4096×216
: 4096/32768
1/8
16384
16384
4096
2
16
: 4096/32768
1/8

hex 
4000×4000=1000×216
4000
4000
1000
2
16

Table 3
fractional 
0.125×0.75=0.093750
0.125
0.75
0.093750

decimal 
4096×24576=1536×216
: 1536/32768
0.046875
4096
24576
1536
2
16
: 1536/32768
0.046875

hex 
1000×6000=0600×216
1000
6000
0600
2
16

You may wish touse the MATLAB commands hex2dec
and dec2hex
.
When we do the multiplication, we are primarily interested in
the top 16 bits of the result, since these are the data that
are actually used when we store the result back into memory
and send it out to the digitaltoanalog converter. (The
entire result is actually stored in the accumulator, so
rounding errors do not accumulate when we do a sequence of
multiplyaccumulate operations in the accumulators.) As the
example above shows, the top 16 bits of the result of
multiplying the fixed point fractional numbers together is
half the expected fractional result. The extra left shift
multiplies the result by two, giving us the correct final
product.
The leftshift requirement can alternatively be explained by
way of decimal place alignment. Remember that when we
multiply decimal numbers, we first multiply them ignoring the
decimal points, then put the decimal point back in the last
step. The decimal point is placed so that the total number of
digits right of the decimal point in the multiplier and
multiplicand is equal to the number of digits right of the
decimal point in their product. The same applies here; the
"decimal point" is to the right of the leftmost (sign) bit,
and there are 15 bits (digits) to the right of this point. So
there are a total of 30 bits to the right of the decimal in
the source. But if we do not shift the result, there are 31
bits to the right of the decimal in the 32bit result. So we
shift the number to the left by one bit, which effectively
reduces the number of bits right of the decimal to 30.
Before the numbers are multiplied by the ALU, each term is
signextended generating a 17bit number from the
16bit input. Because the examples presented above are all
positive, the effect of this sign extension is simply adding
an extra "0" bit at the top of the register
(i.e., positive numbers are not affected by
the sign extension). As the following example illustrates,
not including this signbit for negative numbers produces
erroneous results.
Table 4
fractional 
0.5×0.5=0.25
0.5
0.5
0.25

decimal 
49152×16384=12288×216
: 12288/32678
0.375
49152
16384
12288
2
16
: 12288/32678
0.375

hex 
C000×4000=30000000=3000×216
C000
4000
30000000
3000
2
16

Note that even after the result is leftshifted by one bit
following the multiply, the top bit of the result is still
"0", implying that the result is incorrectly interpreted as a
positive number.
To correct this problem, the ALU signextends negative
multipliers and multiplicands by placing a "1" instead of a
"0" in the added bit. This is called sign
extension because the sign bit is "extended" to the
left another place, adding an extra bit to the left of the
number without changing the number's value.
Table 5
fractional 
0.5×0.5=0.25
0.5
0.5
0.25

hex 
1C000×4000=70000000=7000×216
1C000
4000
70000000
7000
2
16

Although the top bit of this result is still "0", after the
final 1bit leftshift the result is E000 000h
which is a negative number (the top bit is "1"). To check the
final answer, we can negate the product using the two's
complement method described above. After flipping all of the
bits we have 1FFF FFFFh
, and adding one yields
2000 0000h
, which equals 0.25 when interpreted as
an 32 bit fractional number.
"Doug course at UIUC using the TI C54x DSP has been adopted by many EE, CE and CS depts Worldwide "