]> Creatis software - CreaPhase.git/blob - octave_packages/communications-1.1.1/encode.m
Add a useful package (from Source forge) for octave
[CreaPhase.git] / octave_packages / communications-1.1.1 / encode.m
1 ## Copyright (C) 2003 David Bateman
2 ##
3 ## This program is free software; you can redistribute it and/or modify it under
4 ## the terms of the GNU General Public License as published by the Free Software
5 ## Foundation; either version 3 of the License, or (at your option) any later
6 ## version.
7 ##
8 ## This program is distributed in the hope that it will be useful, but WITHOUT
9 ## ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10 ## FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
11 ## details.
12 ##
13 ## You should have received a copy of the GNU General Public License along with
14 ## this program; if not, see <http://www.gnu.org/licenses/>.
15
16 ## -*- texinfo -*-
17 ## @deftypefn {Function File} {@var{code} =} encode (@var{msg},@var{n},@var{k})
18 ## @deftypefnx {Function File} {@var{code} =} encode (@var{msg},@var{n},@var{k},@var{typ})
19 ## @deftypefnx {Function File} {@var{code} =} encode (@var{msg},@var{n},@var{k},@var{typ},@var{opt})
20 ## @deftypefnx {Function File} {[@var{code}, @var{added}] =} encode (@var{...})
21 ##
22 ## Top level block encoder. This function makes use of the lower level
23 ## functions such as @dfn{cyclpoly}, @dfn{cyclgen}, @dfn{hammgen}, and
24 ## @dfn{bchenco}. The message to code is pass in @var{msg}, the
25 ## codeword length is @var{n} and the message length is @var{k}. This 
26 ## function is used to encode messages using either:
27 ##
28 ## @table @asis
29 ## @item A [n,k] linear block code defined by a generator matrix
30 ## @item A [n,k] cyclic code defined by a generator polynomial
31 ## @item A [n,k] Hamming code defined by a primitive polynomial
32 ## @item A [n,k] BCH code code defined by a generator polynomial
33 ## @end table
34 ##
35 ## The type of coding to use is defined by the variable @var{typ}. This 
36 ## variable is a string taking one of the values
37 ##
38 ## @table @code
39 ## @item 'linear' or 'linear/binary'
40 ## A linear block code is assumed with the coded message @var{code} being in 
41 ## a binary format. In this case the argument @var{opt} is the generator
42 ## matrix, and is required.
43 ## @item 'cyclic' or 'cyclic/binary'
44 ## A cyclic code is assumed with the coded message @var{code} being in a
45 ## binary format. The generator polynomial to use can be defined in @var{opt}.
46 ## The default generator polynomial to use will be 
47 ## @dfn{cyclpoly(@var{n},@var{k})}
48 ## @item 'hamming' or 'hamming/binary'
49 ## A Hamming code is assumed with the coded message @var{code} being in a
50 ## binary format. In this case @var{n} must be of an integer of the form
51 ## @code{2^@var{m}-1}, where @var{m} is an integer. In addition @var{k}
52 ## must be @code{@var{n}-@var{m}}. The primitive polynomial to use can 
53 ## be defined in @var{opt}. The default primitive polynomial to use is
54 ## the same as defined by @dfn{hammgen}.
55 ## @item 'bch' or 'bch/binary'
56 ## A BCH code is assumed with the coded message @var{code} being in a binary
57 ## format. The generator polynomial to use can be defined in @var{opt}.
58 ## The default generator polynomial to use will be 
59 ## @dfn{bchpoly(@var{n},@var{k})}
60 ## @end table
61 ##
62 ## In addition the argument 'binary' above can be replaced with 'decimal',
63 ## in which case the message is assumed to be a decimal vector, with each
64 ## value representing a symbol to be coded. The binary format can be in two
65 ## forms
66 ##
67 ## @table @code
68 ## @item An @var{x}-by-@var{k} matrix
69 ## Each row of this matrix represents a symbol to be coded
70 ## @item A vector 
71 ## The symbols are created from groups of @var{k} elements of this vector.
72 ## If the vector length is not divisble by @var{k}, then zeros are added
73 ## and the number of zeros added is returned in @var{added}.
74 ## @end table
75 ##
76 ## It should be noted that all internal calculations are performed in the
77 ## binary format. Therefore for large values of @var{n}, it is preferable
78 ## to use the binary format to pass the messages to avoid possible rounding
79 ## errors. Additionally, if repeated calls to @dfn{encode} will be performed,
80 ## it is often faster to create a generator matrix externally with the 
81 ## functions @dfn{hammgen} or @dfn{cyclgen}, rather than let @dfn{encode}
82 ## recalculate this matrix at each iteration. In this case @var{typ} should
83 ## be 'linear'. The exception to this case is BCH codes, whose encoder 
84 ## is implemented directly from the polynomial and is significantly faster.
85 ##
86 ## @end deftypefn
87 ## @seealso{decode,cyclgen,cyclpoly,hammgen,bchenco,bchpoly}
88
89 function [code, added] = encode(msg, n, k, typ, opt)
90
91   if ((nargin < 3) || (nargin > 5))
92     usage ("[code, added] = encode (msg, n, k [, typ [, opt]])");
93   endif
94
95   if (!isscalar(n) || (n != floor(n)) || (n < 3))
96     error ("encode: codeword length must be an integer greater than 3");
97   endif
98
99   if (!isscalar(k) || (k != floor(k)) || (k > n))
100     error ("encode: message length must be an integer less than codeword length");
101   endif
102
103   if (nargin > 3)
104     if (!ischar(typ))
105       error ("encode: type argument must be a string");
106     else
107       ## Why the hell did matlab decide on such an ugly way of passing 2 args!
108       if (strcmp(typ,"linear") || strcmp(typ,"linear/binary"))
109               coding = "linear";
110               msgtyp = "binary";
111       elseif (strcmp(typ,"linear/decimal"))
112               coding = "linear";
113               msgtyp = "decimal";
114       elseif (strcmp(typ,"cyclic") || strcmp(typ,"cyclic/binary"))
115               coding = "cyclic";
116               msgtyp = "binary";
117       elseif (strcmp(typ,"cyclic/decimal"))
118               coding = "cyclic";
119               msgtyp = "decimal";
120       elseif (strcmp(typ,"bch") || strcmp(typ,"bch/binary"))
121               coding = "bch";
122               msgtyp = "binary";
123       elseif (strcmp(typ,"bch/decimal"))
124               coding = "bch";
125               msgtyp = "decimal";
126       elseif (strcmp(typ,"hamming") || strcmp(typ,"hamming/binary"))
127               coding = "hamming";
128               msgtyp = "binary";
129       elseif (strcmp(typ,"hamming/decimal"))
130               coding = "hamming";
131               msgtyp = "decimal";
132       else
133               error ("encode: unrecognized coding and/or message type");
134       endif
135     endif
136   else
137     coding = "hamming";
138     msgtyp = "binary";
139   endif
140
141   added = 0;
142   if (strcmp(msgtyp,"binary"))
143     vecttyp = 0;
144     if ((max(msg(:)) > 1) || (min(msg(:)) < 0))
145       error ("encode: illegal value in message");
146     endif
147     [ncodewords, k2] = size(msg);
148     len = k2*ncodewords;
149     if (min(k2,ncodewords) == 1)
150       vecttyp = 1;
151       msg = vec2mat(msg,k);
152       ncodewords = size(msg,1);
153     elseif (k2 != k)
154       error ("encode: message matrix must be k columns wide");
155     endif
156   else
157     if (!isvector(msg))
158       error ("encode: decimally encoded message must be a vector");
159     endif
160     if ((max(msg) > 2^k-1) || (min(msg) < 0))
161       error ("encode: illegal value in message");
162     endif
163     ncodewords = length(msg);
164     msg = de2bi(msg(:),k);
165   endif
166
167   if (strcmp(coding,"bch"))
168     if (nargin > 4)
169       code = bchenco(msg,n,k,opt);
170     else
171       code = bchenco(msg,n,k);
172     endif
173   else
174     if (strcmp(coding,"linear"))
175       if (nargin > 4)
176               gen = opt;
177               if ((size(gen,1) != k) || (size(gen,2) != n))
178                 error ("encode: generator matrix is in incorrect form");
179               endif
180       else
181               error ("encode: linear coding must supply the generator matrix");
182       endif
183     elseif (strcmp(coding,"cyclic"))
184       if (nargin > 4)
185               [par, gen] = cyclgen(n,opt);
186       else
187               [par, gen] = cyclgen(n,cyclpoly(n,k));
188       endif
189     else
190       m = log2(n + 1);
191       if ((m != floor(m)) || (m < 3) || (m > 16))
192               error ("encode: codeword length must be of the form '2^m-1' with integer m");
193       endif
194       if (k != (n-m))
195               error ("encode: illegal message length for hamming code");
196       endif
197       if (nargin > 4)
198               [par, gen] = hammgen(m, opt);
199       else
200               [par, gen] = hammgen(m);
201       endif
202     endif
203     code = mod(msg * gen, 2);
204   endif
205
206   if (strcmp(msgtyp,"binary") && (vecttyp == 1))
207     code = code';
208     code = code(:);
209   elseif (strcmp(msgtyp,"decimal"))
210     code = bi2de(code);
211   endif
212
213 endfunction