{"id":4009,"date":"2021-11-20T09:31:53","date_gmt":"2021-11-20T09:31:53","guid":{"rendered":"http:\/\/www.raymaps.com\/?p=4009"},"modified":"2022-06-03T11:04:48","modified_gmt":"2022-06-03T11:04:48","slug":"low-density-parity-check-codes","status":"publish","type":"post","link":"https:\/\/www.raymaps.com\/index.php\/low-density-parity-check-codes\/","title":{"rendered":"Low Density Parity Check Codes"},"content":{"rendered":"\n<p>We have\npreviously discussed Block Codes and Convolutional Codes and their coding and\ndecoding techniques particularly syndrome-based decoding and Viterbi decoding.\nNow we discuss an advanced form of Block Codes known as Low Density Parity\nCheck (LDPC) codes. These codes were first proposed by Robert Gallager in 1960\nbut they did not get immediate recognition as they were quite cumbersome to\ncode and decode. But in 1995 the interest in these codes was revived, after\ndiscovery of Turbo Codes. Both these codes achieve the Shannon Limit and have\nbeen adopted in many wireless communication systems including 5G.<\/p>\n\n\n\n<!--more-->\n\n\n\n<p>The name LDPC originates from the fact that the parity check matrix of LDPC codes is a sparse matrix with a few ones and lots of zeros e.g., a size 1000 x 2000 parity check matrix might have 3 ones per column and 6 ones per row. This simplifies coding and decoding of LDPC codes. Another point to mention here is that LDPC codes draw their inspiration from Turbo Codes which are iteratively decoded, successively getting closer to the Shannon limit. LDPC codes can be decoded in a number of ways but the most common is serial decoding and parallel decoding, both iterative in nature. We discuss parallel decoding in this post. <\/p>\n\n\n\n<p>If you understand coding and decoding of Block Codes, then half the problem is solved. Let\u2019s consider we have 6 data bits (d1, d2, d3, d4, d5, d6) and 5 parity check bits (p1, p2, p3, p4, p5) that are calculated as per the table below. <\/p>\n\n\n\n<table class=\"wp-block-table\"><tbody><tr><td>d1<\/td><td>d2<\/td><td>d3<\/td><td><em>p1<\/em><\/td><\/tr><tr><td>d4<\/td><td>d5<\/td><td>d6<\/td><td><em>p2<\/em><\/td><\/tr><tr><td><em>p3<\/em><\/td><td><em>p4<\/em><\/td><td><em>p5<\/em><\/td><td><\/td><\/tr><\/tbody><\/table>\n\n\n\n<p style=\"text-align:center\">Structure for Calculating Parity Check Bits<\/p>\n\n\n\n<p>The advantage of such a scheme is that each data bit is protected by multiple parity check bits so the possibility of an error going undetected is reduced. The equations that govern the calculation of parity bits are given below. The bit addition operations are performed modulo-2 (equivalent to XOR operation). <\/p>\n\n\n<p style=\"text-align: center;\">p1=d1\u2295d2\u2295d3<\/p>\n<p style=\"text-align: center;\">p2=d4\u2295d5\u2295d6<\/p>\n<p style=\"text-align: center;\">p3=d1\u2295d4<\/p>\n<p style=\"text-align: center;\">p4=d2\u2295d5<\/p>\n<p style=\"text-align: center;\">p5=d3\u2295d6<\/p>\n\n\n<p>It must be noted that during each transmission 6 data bits are transmitted as it is and 5 parity bits are appended to the data bits resulting in a block size of 11. As discussed previously such a code is called systematic code and can easily be encoded and decoded using a generator matrix (G=I|C)&nbsp;and parity check matrix (H=C&#8217;|I) respectively. Another important metric of a code is the code rate which governs how much redundancy is added to the uncoded data bits. The code rate in the above example is r=k\/n=6\/11. Lower the code rate higher is the redundancy and stronger is the code but this is at the expense of spectral efficiency. Typical code rates used in wireless communication systems are 1\/3, 1\/2, 2\/3 etc.<\/p>\n\n\n\n<p>Just as in Block Codes, error detection and correction can be performed by calculating the syndrome but BER performance using this technique is not that great. Maximum Likelihood technique (remember brute search) can be used but it is very computationally complex for large block sizes. Here comes to our rescue a concept from probability theory called Bayes theorem. According to this theorem we can use posterior probabilities to decide which symbol was most likely to have been transmitted. After some simplifications to the Bayes theorem and some more mathematical manipulations we have the following equality.<\/p>\n\n\n\n<p style=\"text-align:center\">L(x1 \u2295 x2) = sgn[L(x1)] sgn[L(x2)] min[|L(x1)|, |L(x2)|]<\/p>\n\n\n\n<p>With this equality and parity check equations given above, the\nextrinsic information of each decoder can be calculated separately (decoder-I operates\nrow wise and decoder-II operates column wise in the above table). This extrinsic\ninformation is then used to refine the estimation of the symbol that was most\nlikely to have been transmitted. The sign is used to estimate the transmitted\nsymbol sign and the absolute value provides the information about the\nreliability of the decoded symbol. As this process is iteratively performed the\nestimate of the transmitted symbol becomes more and more accurate (we have used\nup to 25 iterations in our simulations with improving results). <\/p>\n\n\n\n<p>Let us explain the above concepts with an example. Let us consider the following parity check equation of encoder-I.<\/p>\n\n\n\n<p style=\"text-align:center\"> p1=d1\u2295d2\u2295d3 <\/p>\n\n\n\n<p>If we want to estimate the value of d1 we can rearrange the above equation as follows.<\/p>\n\n\n\n<p style=\"text-align:center\">d1=p1\u2295d2\u2295d3<\/p>\n\n\n\n<p>But in this equation, we have XOR operation being performed on the data bits d2, d3                            and parity bit p1. How do we perform the same operation when we have soft metrics? For this we use the following equality.<\/p>\n\n\n\n<p style=\"text-align:center\">L(d1)=L(p1\u2295d2\u2295d3)=sgn[L(p1)] sgn[L(d2)] sgn[L(d3)] min[|L(p1), |L(d2)|, |L(d3)|]<\/p>\n\n\n\n<p>The L values are described as LLR values or as Log Likelihood Ratios. If one knows the L values of p1, d2 and d3 we can easily calculate the likelihood of d1. The same procedure applies to all other bits and it produces the required extrinsic operation. If we use hard decisions in the above equations, we would get a much inferior bit error rate (this has been verified through simulation). <\/p>\n\n\n\n<pre lang=\"MATLAB\">%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n% ENCODING AND DECODING OF LDPC CODES\n%\n% k=6, n=11, r=6\/11\n% EbNo on Linear Scale\n% 25 Iterations                    \t\t           \n% Copyright 2020 RAYmaps\n%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\nclear all\nclose all\n\nk=6;\nn=11;\nEb=1.0*(n\/k);\nEbNo=10;\n\na=round(rand(1,k));\nC=[1 0 1 0 0;\n   1 0 0 1 0;\n   1 0 0 0 1;\n   0 1 1 0 0;\n   0 1 0 1 0;\n   0 1 0 0 1]; \nI=eye(k,k);\nG=[I,C];\nb=mod(a*G,2);\nc=1-2*b;\nsigma=sqrt(Eb\/(2*EbNo));\nc=c+sigma*randn(1,n);\n\nI=eye(n-k,n-k);\nH=[C',I];\nLc_y=2\/(sigma^2)*c;\nL1=zeros(1,n);\nL2=zeros(1,n);\n\nfor iter=1:25\n  L1(1)=sign(c(2))*sign(c(3))*sign(c(7))*min(abs([c(2),c(3),c(7)]));\n  L1(2)=sign(c(1))*sign(c(3))*sign(c(7))*min(abs([c(1),c(3),c(7)]));\n  L1(3)=sign(c(1))*sign(c(2))*sign(c(7))*min(abs([c(1),c(2),c(7)]));\n  L1(4)=sign(c(5))*sign(c(6))*sign(c(8))*min(abs([c(5),c(6),c(8)]));\n  L1(5)=sign(c(4))*sign(c(6))*sign(c(8))*min(abs([c(4),c(6),c(8)]));\n  L1(6)=sign(c(4))*sign(c(5))*sign(c(8))*min(abs([c(4),c(5),c(8)]));\n  L1(7)=sign(c(1))*sign(c(2))*sign(c(3))*min(abs([c(1),c(2),c(3)]));\n  L1(8)=sign(c(4))*sign(c(5))*sign(c(6))*min(abs([c(4),c(5),c(6)]));\n  L1(9)=0;\n  L1(10)=0;\n  L1(11)=0;\n\n  L2(1)=sign(c(4))*sign(c(9))*min(abs([c(4),c(9)]));\n  L2(2)=sign(c(5))*sign(c(10))*min(abs([c(5),c(10)]));\n  L2(3)=sign(c(6))*sign(c(11))*min(abs([c(6),c(11)]));\n  L2(4)=sign(c(1))*sign(c(9))*min(abs([c(1),c(9)]));\n  L2(5)=sign(c(2))*sign(c(10))*min(abs([c(2),c(10)]));\n  L2(6)=sign(c(3))*sign(c(11))*min(abs([c(3),c(11)]));\n  L2(7)=0;\n  L2(8)=0;\n  L2(9)=sign(c(1))*sign(c(4))*min(abs([c(1),c(4)]));\n  L2(10)=sign(c(2))*sign(c(5))*min(abs([c(2),c(5)]));\n  L2(11)=sign(c(3))*sign(c(6))*min(abs([c(3),c(6)]));\n\n  L_sum=Lc_y+L1+L2;\n  c=L_sum;\n  Lc_y=2\/(sigma^2)*c;\n\n  if sum(mod(H*((1-sign(c))\/2)',2))==0\n      break\n  end\nend\nc=sign(c);\nd=(1-c)\/2;\nber=sum(a(1:k)~=d(1:k))\/k;\n%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n<\/pre>\n\n\n\n<p>The BER results show that great performance gains can be achieved over the no coding case at low to moderate signal to noise ratios. When compared with other Block Codes it is seen that this scheme achieves the same BER performance as Hamming Code (7,4) with Maximum Likelihood Decoding. This is quite an encouraging result because this is achieved with the simplest LDPC code we could imagine. With more complex codes the improvement in BER can be significant. <\/p>\n\n\n\n<figure class=\"wp-block-image\"><img loading=\"lazy\" decoding=\"async\" width=\"560\" height=\"420\" src=\"http:\/\/www.raymaps.com\/wp-content\/uploads\/2021\/11\/BER-Performance-of-LDPC-Codes.png\" alt=\"BER Performance of LDPC Codes\" class=\"wp-image-4028\" srcset=\"https:\/\/www.raymaps.com\/wp-content\/uploads\/2021\/11\/BER-Performance-of-LDPC-Codes.png 560w, https:\/\/www.raymaps.com\/wp-content\/uploads\/2021\/11\/BER-Performance-of-LDPC-Codes-300x225.png 300w\" sizes=\"auto, (max-width: 560px) 100vw, 560px\" \/><figcaption>BER Performance of LDPC Codes<\/figcaption><\/figure>\n\n\n\n<p>Reference<\/p>\n\n\n\n<p>[1] Tilo Strutz,\n\u201cLow Density Parity Check Codes \u2013 An Introduction\u201d, June 09, 2016<\/p>\n\n\n\n<p><a href=\"http:\/\/www1.hft-leipzig.de\/strutz\/Kanalcodierung\/ldpc_introduction.pdf\">http:\/\/www1.hft-leipzig.de\/strutz\/Kanalcodierung\/ldpc_introduction.pdf<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>LDPC codes were first proposed by Robert Gallager in 1960 but they did not get immediate recognition as they were quite cumbersome to code and decode. But in 1995 the interest in these codes was revived, after discovery of Turbo Codes. Both these codes achieve the Shannon Limit and have been adopted in many wireless communication systems including 5G.<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[189,11,10,7],"tags":[195,34,234,132,233],"class_list":["post-4009","post","type-post","status-publish","format-standard","hentry","category-5g","category-berp","category-chancod","category-sim","tag-5g","tag-ber","tag-block-codes","tag-channel-coding","tag-ldpc"],"_links":{"self":[{"href":"https:\/\/www.raymaps.com\/index.php\/wp-json\/wp\/v2\/posts\/4009","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.raymaps.com\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.raymaps.com\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.raymaps.com\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.raymaps.com\/index.php\/wp-json\/wp\/v2\/comments?post=4009"}],"version-history":[{"count":16,"href":"https:\/\/www.raymaps.com\/index.php\/wp-json\/wp\/v2\/posts\/4009\/revisions"}],"predecessor-version":[{"id":4268,"href":"https:\/\/www.raymaps.com\/index.php\/wp-json\/wp\/v2\/posts\/4009\/revisions\/4268"}],"wp:attachment":[{"href":"https:\/\/www.raymaps.com\/index.php\/wp-json\/wp\/v2\/media?parent=4009"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.raymaps.com\/index.php\/wp-json\/wp\/v2\/categories?post=4009"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.raymaps.com\/index.php\/wp-json\/wp\/v2\/tags?post=4009"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}