?? mathhalf.c
字號:
/*
2.4 kbps MELP Proposed Federal Standard speech coder
Fixed-point C code, version 1.0
Copyright (c) 1998, Texas Instruments, Inc.
Texas Instruments has intellectual property rights on the MELP
algorithm. The Texas Instruments contact for licensing issues for
commercial and non-government use is William Gordon, Director,
Government Contracts, Texas Instruments Incorporated, Semiconductor
Group (phone 972 480 7442).
The fixed-point version of the voice codec Mixed Excitation Linear
Prediction (MELP) is based on specifications on the C-language software
simulation contained in GSM 06.06 which is protected by copyright and
is the property of the European Telecommunications Standards Institute
(ETSI). This standard is available from the ETSI publication office
tel. +33 (0)4 92 94 42 58. ETSI has granted a license to United States
Department of Defense to use the C-language software simulation contained
in GSM 06.06 for the purposes of the development of a fixed-point
version of the voice codec Mixed Excitation Linear Prediction (MELP).
Requests for authorization to make other use of the GSM 06.06 or
otherwise distribute or modify them need to be addressed to the ETSI
Secretariat fax: +33 493 65 47 16.
*/
/***************************************************************************
*
* File Name: mathhalf.c
*
* Purpose: Contains functions which implement the primitive
* arithmetic operations.
*
* The functions in this file are listed below. Some of them are
* defined in terms of other basic operations. One of the
* routines, saturate() is static. This is not a basic
* operation, and is not reference outside the scope of this
* file.
*
*
* abs_s()
* add()
* divide_s()
* extract_h()
* extract_l()
* L_abs()
* L_add()
* L_deposit_h()
* L_deposit_l()
* L_mac()
* L_msu()
* L_mult()
* L_negate()
* L_shift_r()
* L_shl()
* L_shr()
* L_sub()
* mac_r()
* msu_r()
* mult()
* mult_r()
* negate()
* norm_l()
* norm_s()
* round()
* saturate()
* shift_r()
* shl()
* shr()
* sub()
*
**************************************************************************/
#include "typedefs.h"
#include "mathhalf.h"
#include "mathdp31.h"
/***************************************************************************
*
* FUNCTION NAME: saturate
*
* PURPOSE:
*
* Limit the 32 bit input to the range of a 16 bit word.
*
*
* INPUTS:
*
* L_var1
* 32 bit long signed integer (Longword) whose value
* falls in the range
* 0x8000 0000 <= L_var1 <= 0x7fff ffff.
*
* OUTPUTS:
*
* none
*
* RETURN VALUE:
*
* swOut
* 16 bit short signed integer (Shortword) whose value
* falls in the range
* 0xffff 8000 <= swOut <= 0x0000 7fff.
*
* KEYWORDS: saturation, limiting, limit, saturate, 16 bits
*
*************************************************************************/
static Shortword saturate(Longword L_var1)
{
Shortword swOut;
if (L_var1 > SW_MAX)
{
swOut = SW_MAX;
}
else if (L_var1 < SW_MIN)
{
swOut = SW_MIN;
}
else
{
swOut = (Shortword) L_var1;
}
return (swOut);
}
/***************************************************************************
*
* FUNCTION NAME: divide_s
*
* PURPOSE:
*
* Divide var1 by var2. Note that both must be positive, and
* var1 >= var2. The output is set to 0 if invalid input is
* provided.
*
* INPUTS:
*
* var1
* 16 bit short signed integer (Shortword) whose value
* falls in the range 0xffff 8000 <= var1 <= 0x0000 7fff.
* var2
* 16 bit short signed integer (Shortword) whose value
* falls in the range 0xffff 8000 <= var2 <= 0x0000 7fff.
*
* OUTPUTS:
*
* none
*
* RETURN VALUE:
*
* swOut
* 16 bit short signed integer (Shortword) whose value
* falls in the range
* 0xffff 8000 <= swOut <= 0x0000 7fff.
*
* IMPLEMENTATION:
*
* In the case where var1==var2 the function returns 0x7fff. The output
* is undefined for invalid inputs. This implementation returns zero
* and issues a warning via stdio if invalid input is presented.
*
* KEYWORDS: divide
*
*************************************************************************/
Shortword divide_s(Shortword var1, Shortword var2)
{
Longword L_div;
Shortword swOut;
if (var1 < 0 || var2 < 0 || var1 > var2) {
/* undefined output for invalid input into divide_s */
return ((Shortword)0);
}
if (var1 == var2)
return ((Shortword)0x7fff);
L_div = ((0x00008000L * (Longword) var1) / (Longword) var2);
swOut = saturate(L_div);
return (swOut);
}
/***************************************************************************
*
* FUNCTION NAME: L_deposit_l
*
* PURPOSE:
*
* Put the 16 bit input into the 16 LSB's of the output Longword with
* sign extension i.e. the top 16 bits are set to either 0 or 0xffff.
*
* INPUTS:
*
* var1
* 16 bit short signed integer (Shortword) whose value
* falls in the range 0xffff 8000 <= var1 <= 0x0000 7fff.
*
* OUTPUTS:
*
* none
*
* RETURN VALUE:
*
* L_Out
* 32 bit long signed integer (Longword) whose value
* falls in the range
* 0xffff 8000 <= L_var1 <= 0x0000 7fff.
*
* KEYWORDS: deposit, assign
*
*************************************************************************/
Longword L_deposit_l(Shortword var1)
{
Longword L_Out;
L_Out = var1;
return (L_Out);
}
/***************************************************************************
*
* FUNCTION NAME: L_deposit_h
*
* PURPOSE:
*
* Put the 16 bit input into the 16 MSB's of the output Longword. The
* LS 16 bits are zeroed.
*
* INPUTS:
*
* var1
* 16 bit short signed integer (Shortword) whose value
* falls in the range 0xffff 8000 <= var1 <= 0x0000 7fff.
*
* OUTPUTS:
*
* none
*
* RETURN VALUE:
*
* L_Out
* 32 bit long signed integer (Longword) whose value
* falls in the range
* 0x8000 0000 <= L_var1 <= 0x7fff 0000.
*
*
* KEYWORDS: deposit, assign, fractional assign
*
*************************************************************************/
Longword L_deposit_h(Shortword var1)
{
Longword L_var2;
L_var2 = (Longword) var1 << 16;
return (L_var2);
}
/***************************************************************************
*
* FUNCTION NAME: extract_l
*
* PURPOSE:
*
* Extract the 16 LS bits of a 32 bit Longword. Return the 16 bit
* number as a Shortword. The upper portion of the input Longword
* has no impact whatsoever on the output.
*
* INPUTS:
*
* L_var1
* 32 bit long signed integer (Longword) whose value
* falls in the range
* 0x8000 0000 <= L_var1 <= 0x7fff ffff.
*
* OUTPUTS:
*
* none
*
* RETURN VALUE:
*
* swOut
* 16 bit short signed integer (Shortword) whose value
* falls in the range
* 0xffff 8000 <= swOut <= 0x0000 7fff.
*
*
* KEYWORDS: extract, assign
*
*************************************************************************/
Shortword extract_l(Longword L_var1)
{
Shortword var2;
var2 = (Shortword) (0x0000ffffL & L_var1);
return (var2);
}
/***************************************************************************
*
* FUNCTION NAME: extract_h
*
* PURPOSE:
*
* Extract the 16 MS bits of a 32 bit Longword. Return the 16 bit
* number as a Shortword. This is used as a "truncation" of a fractional
* number.
*
* INPUTS:
*
* L_var1
* 32 bit long signed integer (Longword) whose value
* falls in the range
* 0x8000 0000 <= L_var1 <= 0x7fff ffff.
*
* OUTPUTS:
*
* none
*
* RETURN VALUE:
*
* swOut
* 16 bit short signed integer (Shortword) whose value
* falls in the range
* 0xffff 8000 <= swOut <= 0x0000 7fff.
*
* IMPLEMENTATION:
*
* KEYWORDS: assign, truncate
*
*************************************************************************/
Shortword extract_h(Longword L_var1)
{
Shortword var2;
var2 = (Shortword) (0x0000ffffL & (L_var1 >> 16));
return (var2);
}
/***************************************************************************
*
* FUNCTION NAME: round
*
* PURPOSE:
*
* Round the 32 bit Longword into a 16 bit shortword with saturation.
*
* INPUTS:
*
* L_var1
* 32 bit long signed integer (Longword) whose value
* falls in the range
* 0x8000 0000 <= L_var1 <= 0x7fff ffff.
* OUTPUTS:
*
* none
*
* RETURN VALUE:
*
* swOut
* 16 bit short signed integer (Shortword) whose value
* falls in the range
* 0xffff 8000 <= swOut <= 0x0000 7fff.
*
* IMPLEMENTATION:
*
* Perform a two's complement round on the input Longword with
* saturation.
*
* This is equivalent to adding 0x0000 8000 to the input. The
* result may overflow due to the add. If so, the result is
* saturated. The 32 bit rounded number is then shifted down
* 16 bits and returned as a Shortword.
*
*
* KEYWORDS: round
*
*************************************************************************/
Shortword round(Longword L_var1)
{
Longword L_Prod;
Shortword var2;
L_Prod = L_add(L_var1, 0x00008000L); /* round MSP */
var2 = extract_h(L_Prod);
return (var2);
}
/***************************************************************************
*
* FUNCTION NAME: negate
*
* PURPOSE:
*
* Negate the 16 bit input. 0x8000's negated value is 0x7fff.
*
* INPUTS:
*
* var1
* 16 bit short signed integer (Shortword) whose value
* falls in the range 0xffff 8000 <= var1 <= 0x0000 7fff.
*
* OUTPUTS:
*
* none
*
* RETURN VALUE:
*
* swOut
* 16 bit short signed integer (Shortword) whose value
* falls in the range
* 0xffff 8001 <= swOut <= 0x0000 7fff.
*
* KEYWORDS: negate, negative, invert
*
*************************************************************************/
Shortword negate(Shortword var1)
{
Shortword swOut;
if (var1 == SW_MIN) {
swOut = SW_MAX;
}
else {
swOut = -var1;
}
return (swOut);
}
/***************************************************************************
*
* FUNCTION NAME: L_negate
*
* PURPOSE:
*
* Negate the 32 bit input. 0x8000 0000's negated value is
* 0x7fff ffff.
*
* INPUTS:
*
* L_var1
* 32 bit long signed integer (Longword) whose value
* falls in the range
* 0x8000 0000 <= L_var1 <= 0x7fff ffff.
*
* OUTPUTS:
*
* none
*
* RETURN VALUE:
*
* L_Out
* 32 bit long signed integer (Longword) whose value
* falls in the range
* 0x8000 0001 <= L_var1 <= 0x7fff ffff.
*
* KEYWORDS: negate, negative
*
*************************************************************************/
Longword L_negate(Longword L_var1)
{
Longword L_Out;
if (L_var1 == LW_MIN) {
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -