Files
BPI-CM9-Linux/aml-comp/vendor/amlogic/zvbi/src/hamm.c
T
2026-08-24 10:03:24 +08:00

168 lines
3.8 KiB
C

/*
* libzvbi -- Error correction functions
*
* Copyright (C) 2001, 2002, 2003, 2004, 2007 Michael H. Schimek
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
* Boston, MA 02110-1301 USA.
*/
/* $Id: hamm.c,v 1.10 2008/02/19 00:35:20 mschimek Exp $ */
#ifdef HAVE_CONFIG_H
# include "config.h"
#endif
#include <limits.h> /* CHAR_BIT */
#include "hamm.h"
#include "hamm-tables.h"
/**
* @ingroup Error
*
* @param p Array of unsigned bytes.
* @param n Size of array.
*
* Of each byte of the array, changes the most significant
* bit to make the number of set bits odd.
*
* @since 0.2.12
*/
void
vbi_par (uint8_t * p,
unsigned int n)
{
while (n-- > 0) {
uint8_t c = *p;
/* if 0 == (inv_par[] & 32) change msb of *p. */
*p++ = c ^ (128 & ~(_vbi_hamm24_inv_par[0][c] << 2));
}
}
/**
* @ingroup Error
* @param p Array of unsigned bytes.
* @param n Size of array.
*
* Tests the parity and clears the most significant bit of
* each byte of the array.
*
* @return
* A negative value if any byte of the array had even
* parity (sum of bits modulo 2 is 0).
*
* @since 0.2.12
*/
int
vbi_unpar (uint8_t * p,
unsigned int n)
{
int r = 0;
while (n-- > 0) {
uint8_t c = *p;
/* if 0 == (inv_par[] & 32) set msb of r. */
r |= ~ _vbi_hamm24_inv_par[0][c]
<< (sizeof (int) * CHAR_BIT - 1 - 5);
*p++ = c & 127;
}
return r;
}
/**
* @ingroup Error
* @param p A Hamming 24/18 protected 24 bit word will be stored here,
* last significant byte first, lsb first transmitted.
* @param c Integer between 0 ... 1 << 18 - 1.
*
* Encodes an 18 bit word with Hamming 24/18 protection
* as specified in ETS 300 706, Section 8.3.
*
* @since 0.2.27
*/
void
vbi_ham24p (uint8_t * p,
unsigned int c)
{
unsigned int D5_D11;
unsigned int D12_D18;
unsigned int P5, P6;
unsigned int Byte_0;
Byte_0 = (_vbi_hamm24_fwd_0 [(c >> 0) & 0xFF]
^ _vbi_hamm24_fwd_1 [(c >> 8) & 0xFF]
^ _vbi_hamm24_fwd_2 [(c >> 16) & 0x03]);
p[0] = Byte_0;
D5_D11 = (c >> 4) & 0x7F;
D12_D18 = (c >> 11) & 0x7F;
P5 = 0x80 & ~(_vbi_hamm24_inv_par[0][D12_D18] << 2);
p[1] = D5_D11 | P5;
P6 = 0x80 & ((_vbi_hamm24_inv_par[0][Byte_0]
^ _vbi_hamm24_inv_par[0][D5_D11]) << 2);
p[2] = D12_D18 | P6;
}
/**
* @ingroup Error
* @param p Pointer to a Hamming 24/18 protected 24 bit word,
* last significant byte first, lsb first transmitted.
*
* Decodes a Hamming 24/18 protected byte triplet
* as specified in ETS 300 706, Section 8.3.
*
* @return
* Triplet data bits D18 [msb] ... D1 [lsb] or a negative value
* if the triplet contained incorrectable errors.
*
* @since 0.2.12
*/
int
vbi_unham24p (const uint8_t * p)
{
unsigned int D1_D4;
unsigned int D5_D11;
unsigned int D12_D18;
unsigned int ABCDEF;
int32_t d;
D1_D4 = _vbi_hamm24_inv_d1_d4[p[0] >> 2];
D5_D11 = p[1] & 0x7F;
D12_D18 = p[2] & 0x7F;
d = D1_D4 | (D5_D11 << 4) | (D12_D18 << 11);
ABCDEF = (_vbi_hamm24_inv_par[0][p[0]]
^ _vbi_hamm24_inv_par[1][p[1]]
^ _vbi_hamm24_inv_par[2][p[2]]);
/* Correct single bit error, set MSB on double bit error. */
return d ^ (int) _vbi_hamm24_inv_err[ABCDEF];
}
/*
Local variables:
c-set-style: K&R
c-basic-offset: 8
End:
*/