diff mbox series

[RFC/RFA,v2,12/12] Add tests for CRC detection and generation.

Message ID CAE65F3NcSA9Q_xG2OXiR9u8HmFWAFRhsKEY46gB8dkt-BbGZCw@mail.gmail.com
State New
Headers show
Series [RFC/RFA,v2,01/12] Implement internal functions for efficient CRC computation | expand

Commit Message

Mariam Arutunian July 26, 2024, 6:07 p.m. UTC
gcc/testsuite/gcc.dg/torture/

       * crc-(1-29).c: New tests.
       * crc-CCIT-data16-xorOutside_InsideFor.c: Likewise.
       * crc-CCIT-data16.c: Likewise.
       * crc-CCIT-data8.c: Likewise.
       * crc-coremark16-data16.c: Likewise.
       * crc-coremark32-data16.c: Likewise.
       * crc-coremark32-data32.c: Likewise.
       * crc-coremark32-data8.c: Likewise.
       * crc-coremark64-data64.c: Likewise.
       * crc-coremark8-data8.c: Likewise.
       * crc-crc32-data16.c: Likewise.
       * crc-crc32-data24.c: Likewise.
       * crc-crc32-data8.c: Likewise.
       * crc-crc32.c: Likewise.
       * crc-crc64-data32.c: Likewise.
       * crc-crc64-data64.c: Likewise.
       * crc-crc8-data8-loop-xorInFor.c: Likewise.
       * crc-crc8-data8-loop-xorOutsideFor.c: Likewise.
       * crc-crc8-data8-xorOustideFor.c: Likewise.
       * crc-crc8.c: Likewise.
       * crc-linux-(1-5).c: Likewise.
       * crc-not-crc-(1-26).c: Likewise.
       * crc-side-instr-(1-17).c: Likewise.

   Signed-off-by: Mariam Arutunian <mariamarutunian@gmail.com>

Comments

Jeff Law Aug. 25, 2024, 5:28 p.m. UTC | #1
On 7/26/24 12:07 PM, Mariam Arutunian wrote:
>     gcc/testsuite/gcc.dg/torture/
> 
>         * crc-(1-29).c: New tests.
>         * crc-CCIT-data16-xorOutside_InsideFor.c: Likewise.
>         * crc-CCIT-data16.c: Likewise.
>         * crc-CCIT-data8.c: Likewise.
>         * crc-coremark16-data16.c: Likewise.
>         * crc-coremark32-data16.c: Likewise.
>         * crc-coremark32-data32.c: Likewise.
>         * crc-coremark32-data8.c: Likewise.
>         * crc-coremark64-data64.c: Likewise.
>         * crc-coremark8-data8.c: Likewise.
>         * crc-crc32-data16.c: Likewise.
>         * crc-crc32-data24.c: Likewise.
>         * crc-crc32-data8.c: Likewise.
>         * crc-crc32.c: Likewise.
>         * crc-crc64-data32.c: Likewise.
>         * crc-crc64-data64.c: Likewise.
>         * crc-crc8-data8-loop-xorInFor.c: Likewise.
>         * crc-crc8-data8-loop-xorOutsideFor.c: Likewise.
>         * crc-crc8-data8-xorOustideFor.c: Likewise.
>         * crc-crc8.c: Likewise.
>         * crc-linux-(1-5).c: Likewise.
>         * crc-not-crc-(1-26).c: Likewise.
>         * crc-side-instr-(1-17).c: Likewise.
> 
>     Signed-off-by: Mariam Arutunian <mariamarutunian@gmail.com 
> <mailto:mariamarutunian@gmail.com>>
So I can't recall the state on all this stuff.  So I'll go ahead and ACK 
this (perhaps for the Nth time ;-)  Obviously it can't commit until the 
optimization bits are all in place.

Jeff
diff mbox series

Patch

diff --git a/gcc/testsuite/gcc.dg/torture/crc-1.c b/gcc/testsuite/gcc.dg/torture/crc-1.c
new file mode 100644
index 00000000000..d61a7c8027d
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-1.c
@@ -0,0 +1,114 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -fdisable-tree-phiopt2 -fdisable-tree-phiopt3" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stddef.h>
+#include <stdint.h>
+#include <stdlib.h>
+
+#define CRC16 0x8005
+
+__attribute__ ((noinline,optimize(0)))
+uint16_t gen_crc16_O0 (const uint8_t *data, uint16_t size) {
+    uint16_t out = 0;
+    int bits_read = 0, bit_flag;
+
+    if (data == NULL)
+        return 0;
+
+    while (size > 0) {
+        bit_flag = out >> 15;
+
+        out <<= 1;
+        out |= (*data >> bits_read) & 1;
+
+        bits_read++;
+        if (bits_read > 7) {
+            bits_read = 0;
+            data++;
+            size--;
+        }
+
+        if (bit_flag)
+            out ^= CRC16;
+    }
+
+    int i;
+    for (i = 0; i < 16; ++i) {
+        bit_flag = out >> 15;
+        out <<= 1;
+        if (bit_flag)
+            out ^= CRC16;
+    }
+
+    uint16_t crc = 0;
+    i = 0x8000;
+    int j = 0x0001;
+    for (; i != 0; i >>= 1, j <<= 1) {
+        if (i & out) crc |= j;
+    }
+
+    return crc;
+}
+
+uint16_t gen_crc16 (const uint8_t *data, uint16_t size) {
+  uint16_t out = 0;
+  int bits_read = 0, bit_flag;
+
+  if (data == NULL)
+    return 0;
+
+  while (size > 0) {
+      bit_flag = out >> 15;
+
+      out <<= 1;
+      out |= (*data >> bits_read) & 1;
+
+      bits_read++;
+      if (bits_read > 7) {
+	  bits_read = 0;
+	  data++;
+	  size--;
+	}
+
+      if (bit_flag)
+	out ^= CRC16;
+    }
+
+  int i;
+  for (i = 0; i < 16; ++i) {
+      bit_flag = out >> 15;
+      out <<= 1;
+      if (bit_flag)
+	out ^= CRC16;
+    }
+
+  uint16_t crc = 0;
+  i = 0x8000;
+  int j = 0x0001;
+  for (; i != 0; i >>= 1, j <<= 1) {
+      if (i & out) crc |= j;
+    }
+
+  return crc;
+}
+
+int main ()
+{
+  if (gen_crc16 ("hello", 5) != 13522)
+    abort ();
+
+  for (uint8_t i = 0; i < 255; i++)
+    {
+      uint16_t res1 = gen_crc16_O0 (&i, 1);
+      uint16_t res2 = gen_crc16 (&i, 1);
+      if (res1 != res2)
+	abort ();
+    }
+}
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 15" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{\[0, \]*1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1\\\}" "crc" } } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-10.c b/gcc/testsuite/gcc.dg/torture/crc-10.c
new file mode 100644
index 00000000000..abd63dda87a
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-10.c
@@ -0,0 +1,48 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+#define POLY (0x1070U << 3)
+#define u8 uint8_t
+#define u16 uint16_t
+
+ __attribute__ ((noinline,optimize(0)))
+u8 crc8_O0 (u16 data) {
+    int i;
+    for (i = 0; i < 8; i++) {
+        if (data & 0x8000)
+            data = data ^ POLY;
+        data = data << 1;
+    }
+    return (u8)(data >> 8);
+}
+
+u8 crc8 (u16 data) {
+    int i;
+    for (i = 0; i < 8; i++) {
+        if (data & 0x8000)
+            data = data ^ POLY;
+        data = data << 1;
+    }
+    return (u8)(data >> 8);
+}
+
+int main ()
+{
+  for (u8 i = 0; i < 255; i++)
+    {
+      u8 res1 = crc8_O0 (i);
+      u8 res2 = crc8 (i);
+      if (res1 != res2)
+	abort ();
+    }
+}
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0\\\}" "crc" } } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-11.c b/gcc/testsuite/gcc.dg/torture/crc-11.c
new file mode 100644
index 00000000000..baa74a72ee7
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-11.c
@@ -0,0 +1,20 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+//We just don't check cases when the polynomial is a variable, as we can't replace it.
+#include <stdint.h>
+
+uint16_t crc16(uint16_t crc, uint8_t a, uint16_t polynom) {
+  int i;
+  crc ^= a;
+  for (i = 0; i < 8; ++i) {
+      if (crc & 1)
+	crc = (crc >> 1) ^ polynom;
+      else
+	crc = (crc >> 1);
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump "Second operand of the xor statement isn't an integer constant.\n" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-12.c b/gcc/testsuite/gcc.dg/torture/crc-12.c
new file mode 100644
index 00000000000..d9dba304980
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-12.c
@@ -0,0 +1,112 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc -fdisable-tree-phiopt2 -fdisable-tree-phiopt3" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdio.h>
+#include <stdint.h>
+#include <stdlib.h>
+
+#define CRC16 0x8005
+
+__attribute__ ((noinline,optimize(0)))
+uint16_t gen_crc16_O0 (const uint8_t *data, uint16_t size) {
+    uint16_t out = 0;
+    int bits_read = 0, bit_flag;
+
+    if (data == NULL)
+        return 0;
+
+    while (size > 0) {
+        bit_flag = out >> 15;
+
+        out <<= 1;
+        out |= (*data >> bits_read) & 1;
+
+        bits_read++;
+        if (bits_read > 7) {
+            bits_read = 0;
+            data++;
+            size--;
+        }
+
+        if (bit_flag)
+            out ^= CRC16;
+
+    }
+
+    int i;
+    for (i = 0; i < 16; ++i) {
+        bit_flag = out >> 15;
+        out <<= 1;
+        if (bit_flag)
+            out ^= CRC16;
+    }
+
+    uint16_t crc = 0;
+    i = 0x8000;
+    int j = 0x0001;
+    for (; i != 0; i >>= 1, j <<= 1) {
+        if (i & out) crc |= j;
+    }
+
+    return crc;
+}
+
+uint16_t gen_crc16 (const uint8_t *data, uint16_t size) {
+  uint16_t out = 0;
+  int bits_read = 0, bit_flag;
+
+  if (data == NULL)
+    return 0;
+
+  while (size > 0) {
+      bit_flag = out >> 15;
+
+      out <<= 1;
+      out |= (*data >> bits_read) & 1;
+
+      bits_read++;
+      if (bits_read > 7) {
+	  bits_read = 0;
+	  data++;
+	  size--;
+	}
+
+      if (bit_flag)
+	out ^= CRC16;
+
+    }
+
+  int i;
+  for (i = 0; i < 16; ++i) {
+      bit_flag = out >> 15;
+      out <<= 1;
+      if (bit_flag)
+	out ^= CRC16;
+    }
+
+  uint16_t crc = 0;
+  i = 0x8000;
+  int j = 0x0001;
+  for (; i != 0; i >>= 1, j <<= 1) {
+      if (i & out) crc |= j;
+    }
+
+  return crc;
+}
+
+int main ()
+{
+  for (uint8_t i = 0; i < 255; i++)
+    {
+      uint16_t res1 = gen_crc16_O0 (&i, 1);
+      uint16_t res2 = gen_crc16 (&i, 1);
+      if (res1 != res2)
+	abort ();
+    }
+}
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 15" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-13.c b/gcc/testsuite/gcc.dg/torture/crc-13.c
new file mode 100644
index 00000000000..2f75181ca1f
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-13.c
@@ -0,0 +1,58 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+unsigned short crc16_O0 (unsigned char newByte, unsigned short crcValue) {
+  unsigned char i;
+
+  for (i = 0; i < 8; i++) {
+
+      if (((crcValue & 0x8000) >> 8) ^ (newByte & 0x80)) {
+	  crcValue = (crcValue << 1) ^ 0x102;
+	} else {
+	  crcValue = (crcValue << 1);
+	}
+
+      newByte <<= 1;
+    }
+
+  return crcValue;
+}
+
+unsigned short crc16 (unsigned char newByte, unsigned short crcValue) {
+  unsigned char i;
+
+  for (i = 0; i < 8; i++) {
+
+      if (((crcValue & 0x8000) >> 8) ^ (newByte & 0x80)) {
+	  crcValue = (crcValue << 1) ^ 0x102;
+	} else {
+	  crcValue = (crcValue << 1);
+	}
+
+      newByte <<= 1;
+    }
+
+  return crcValue;
+}
+
+int main ()
+{
+  unsigned short crc = 0x0D80;
+  for (unsigned char i = 0; i < 255; i++)
+    {
+      unsigned short res1 = crc16_O0 (crc, i);
+      unsigned short res2 = crc16 (crc, i);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-14.c b/gcc/testsuite/gcc.dg/torture/crc-14.c
new file mode 100644
index 00000000000..f1158a097fd
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-14.c
@@ -0,0 +1,54 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+
+#include <stdlib.h>
+
+typedef unsigned char uint8_t;
+
+__attribute__ ((noinline,optimize(0)))
+uint8_t gencrc_O0 (uint8_t *data)
+{
+  uint8_t crc = 0xff;
+  size_t j;
+  crc ^= *data;
+  for (j = 0; j < 8; j++)
+    {
+      if ((crc & 0x80) != 0)
+	crc = (uint8_t) ((crc << 1) ^ 0x31);
+      else
+	crc <<= 1;
+    }
+  return crc;
+}
+
+uint8_t gencrc (uint8_t *data)
+{
+  uint8_t crc = 0xff;
+  size_t j;
+  crc ^= *data;
+  for (j = 0; j < 8; j++)
+    {
+      if ((crc & 0x80) != 0)
+	crc = (uint8_t) ((crc << 1) ^ 0x31);
+      else
+	crc <<= 1;
+    }
+  return crc;
+}
+
+int main ()
+{
+  for (uint8_t i = 0; i < 255; i++)
+    {
+      uint8_t res1 = gencrc_O0 (&i);
+      uint8_t res2 = gencrc (&i);
+      if (res1 != res2)
+	abort ();
+    }
+}
+
+/* { dg-final { scan-tree-dump "gencrc function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-15.c b/gcc/testsuite/gcc.dg/torture/crc-15.c
new file mode 100644
index 00000000000..9b16253eb0f
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-15.c
@@ -0,0 +1,32 @@ 
+/* { dg-do compile } */
+/* { dg-options "-w -fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+/* Test from busybox, we don't verify as it depends on endian variable.  */
+#include <stdint.h>
+#include <stdlib.h>
+
+uint32_t* crc32_filltable(uint32_t *crc_table, int endian)
+{
+  uint32_t polynomial = endian ? 0x04c11db7 : 0xedb88320;
+  uint32_t c;
+  unsigned i, j;
+
+  if (!crc_table)
+    crc_table = malloc (256 * sizeof (uint32_t));
+
+  for (i = 0; i < 256; i++)
+    {
+      c = endian ? (i << 24) : i;
+      for (j = 8; j; j--)
+	{
+	  if (endian)
+	    c = (c & 0x80000000) ? ((c << 1) ^ polynomial) : (c << 1);
+	  else
+	    c = (c & 1) ? ((c >> 1) ^ polynomial) : (c >> 1);
+	}
+      *crc_table++ = c;
+    }
+
+  return crc_table - 256;
+}
diff --git a/gcc/testsuite/gcc.dg/torture/crc-16.c b/gcc/testsuite/gcc.dg/torture/crc-16.c
new file mode 100644
index 00000000000..35d5651355d
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-16.c
@@ -0,0 +1,40 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+/* A test from busybox - we don't verify, as unsigned is used for the
+  "expected" variable, but 16-bit CRC is calculated.  We verify only those cases
+  when CRC variable's size and calculated CRC are equal. In the algorithm we don't
+  check whether "expected" variable's only low half is used.  */
+int receive(/*int read_fd, */int file_fd)
+{
+  /* Initialization is not the same as in Busybox.  */
+  unsigned blockLength = 13;
+  unsigned char blockBuf[1024] = "sgdfsgdfsgdfs";
+  int cksum_or_crc = 0x4561;
+
+  unsigned expected;
+  int i, j;
+ /* ... */
+  expected = 0;
+      for (i = 0; i < blockLength; i++)
+	{
+	  expected = expected ^ blockBuf[i] << 8;
+	  for (j = 0; j < 8; j++)
+	    {
+	      if (expected & 0x8000)
+		expected = (expected << 1) ^ 0x1021;
+	      else
+		expected = (expected << 1);
+	    }
+	}
+      expected &= 0xffff;
+
+  if (cksum_or_crc != expected) {
+      /* ... */
+      return 1; // was - goto timout
+    }
+
+  /* ... */
+  return -1;
+}
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-17.c b/gcc/testsuite/gcc.dg/torture/crc-17.c
new file mode 100644
index 00000000000..d1b39f51762
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-17.c
@@ -0,0 +1,72 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+unsigned short calc_crc_O0 (unsigned short crc, unsigned char data)
+{
+ unsigned int i, j, org, dst;
+ org = data;
+ dst = 0;
+
+ for (i = 0; i < 8; i++) {
+  org <<= 1;
+  dst >>= 1;
+  if (org & 0x100)
+   dst |= 0x80;
+ }
+ data = (unsigned char) dst;
+ crc ^= (unsigned int) data << (16 - 8);
+ for (j = 0; j < 8; j++) {
+  if (crc & 0x8000U)
+   crc = (crc << 1) ^ 0x1021U ;
+  else
+   crc <<= 1 ;
+ }
+ return crc;
+}
+
+unsigned short calc_crc (unsigned short crc, unsigned char data)
+{
+  unsigned int i, j, org, dst;
+  org = data;
+  dst = 0;
+
+  for (i = 0; i < 8; i++) {
+      org <<= 1;
+      dst >>= 1;
+      if (org & 0x100)
+	dst |= 0x80;
+    }
+  data = (unsigned char) dst;
+  crc ^= (unsigned int) data << (16 - 8);
+  for (j = 0; j < 8; j++) {
+      if (crc & 0x8000U)
+	crc = (crc << 1) ^ 0x1021U ;
+      else
+	crc <<= 1 ;
+    }
+  return crc;
+}
+
+
+int main ()
+{
+  unsigned short crc = 0x0D80;
+  for (unsigned char i = 0; i < 255; i++)
+    {
+      unsigned short res1 = calc_crc_O0 (crc, i);
+      unsigned short res2 = calc_crc (crc, i);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+/* { dg-final { scan-tree-dump "calc_crc function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Polynomial's value is \\\{\[0, \]*1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1\\\}" 1 "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-18.c b/gcc/testsuite/gcc.dg/torture/crc-18.c
new file mode 100644
index 00000000000..d43832f4e2f
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-18.c
@@ -0,0 +1,42 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+unsigned char crc8_O0 (unsigned char value)
+{
+    for (int i = 0; i < 8; ++i) {
+        value = (value & 0x80) ? ((value << 1) ^ 0x31) : (value << 1);
+    }
+
+    return value;
+}
+
+unsigned char crc8 (unsigned char value)
+{
+  for (int i = 0; i < 8; ++i) {
+      value = (value & 0x80) ? ((value << 1) ^ 0x31) : (value << 1);
+    }
+
+  return value;
+}
+
+int main ()
+{
+  for (unsigned char i = 0; i < 255; i++)
+    {
+      unsigned char res1 = crc8_O0 (i);
+      unsigned char res2 = crc8 (i);
+      if (res1 != res2)
+	abort ();
+    }
+}
+
+/* { dg-final { scan-tree-dump "crc8 function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{\[0, \]*0, 0, 1, 1, 0, 0, 0, 1\\\}" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-19.c b/gcc/testsuite/gcc.dg/torture/crc-19.c
new file mode 100644
index 00000000000..f3d841c62bf
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-19.c
@@ -0,0 +1,30 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+ #include <stdint.h>
+
+ uint32_t crc24_reverse(uint32_t crc, const uint8_t *data, uint8_t len)
+ {
+   uint32_t state = crc;
+   uint8_t i;
+
+   for (i = 0; i < len; i++) {
+       uint8_t n, cur = data[len - i - 1];
+
+       for (n = 0; n < 8; n++) {
+	   int top_bit = state >> 23;
+
+	   state = (state << 1) & 0xffffff;
+	   state |= top_bit ^ ((cur >> (7 - n)) & 1);
+	   if (top_bit)
+	     state ^= 0xb4c000;
+	 }
+     }
+
+   return state;
+ }
+
+/* { dg-final { scan-tree-dump "crc24_reverse function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-2.c b/gcc/testsuite/gcc.dg/torture/crc-2.c
new file mode 100644
index 00000000000..139fb49fc05
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-2.c
@@ -0,0 +1,28 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#define CRC16_CCITT     0x102
+#define POLYNOM         CRC16_CCITT
+
+unsigned int crc16 (unsigned int crcValue, unsigned char newByte) {
+    unsigned char i;
+
+    for (i = 0; i < 8; i++) {
+
+        if (((crcValue & 0x8000) >> 8) ^ (newByte & 0x80)) {
+            crcValue = (crcValue << 1) ^ POLYNOM;
+        } else {
+            crcValue = (crcValue << 1);
+        }
+
+        newByte <<= 1;
+    }
+
+    return crcValue;
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{\[0, \]*1, 0, 0, 0, 0, 0, 0, 1, 0\\\}" "crc" } } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-20.c b/gcc/testsuite/gcc.dg/torture/crc-20.c
new file mode 100644
index 00000000000..8bd10445745
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-20.c
@@ -0,0 +1,39 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+/* We don't detect this case, because there are many conditional branches.
+    Even if we detected it won't be verified,
+    because we would get more than two execution paths (states).  */
+
+#include <stdint.h>
+
+typedef uint8_t byte;
+byte Compute_CRC8_Simple_OneByte_ShiftReg (byte byteVal)
+{
+  const byte generator = 0x1D;
+  byte crc = 0; /* init crc register with 0 */
+  byte b = byteVal;
+  for (int i = 7; i >= 0; i--)
+    {
+      /* check if MSB is set */
+      if ((crc & 0x80) != 0)
+	{   /* MSB set, shift it out of the register */
+	  crc = (byte) (crc << 1);
+	  /* shift in next bit of input stream:
+	   * If it's 1, set LSB of crc to 1.
+	   * If it's 0, set LSB of crc to 0. */
+	  crc = ((byte) (b & (1 << i)) != 0) ? (byte) (crc | 0x01)
+					     : (byte) (crc & 0xFE);
+	  /* Perform the 'division' by XORing the crc register with the generator polynomial */
+	  crc = (byte) (crc ^ generator);
+	}
+      else
+	{   /* MSB not set, shift it out and shift in next bit of input stream. Same as above, just no division */
+	  crc = (byte) (crc << 1);
+	  crc = ((byte) (b & (1 << i)) != 0) ? (byte) (crc | 0x01)
+					     : (byte) (crc & 0xFE);
+	}
+    }
+  return crc;
+}
diff --git a/gcc/testsuite/gcc.dg/torture/crc-21.c b/gcc/testsuite/gcc.dg/torture/crc-21.c
new file mode 100644
index 00000000000..28e7ea6a305
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-21.c
@@ -0,0 +1,53 @@ 
+/* { dg-do run { target { lp64 } } } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+uint32_t _crc32_O0 (uint32_t crc, uint32_t data) {
+  int i;
+  crc = crc ^ data;
+
+  for (i = 0; i < 32; i++) {
+      if (crc & 0x80000000)
+	crc = (crc << 1) ^ 0x04C11DB7;
+      else
+	crc = (crc << 1);
+    }
+
+  return crc;
+}
+
+uint32_t _crc32 (uint32_t crc, uint32_t data) {
+  int i;
+  crc = crc ^ data;
+
+  for (i = 0; i < 32; i++) {
+      if (crc & 0x80000000)
+	crc = (crc << 1) ^ 0x04C11DB7;
+      else
+	crc = (crc << 1);
+    }
+
+  return crc;
+}
+
+int main ()
+{
+  uint32_t crc = 0x0D800D80;
+  for (uint32_t i = 0; i < 0xff; i++)
+    {
+      uint32_t res1 = _crc32_O0 (crc, i);
+      uint32_t res2 = _crc32 (crc, i);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+/* { dg-final { scan-tree-dump "_crc32 function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 31" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC." "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-22.c b/gcc/testsuite/gcc.dg/torture/crc-22.c
new file mode 100644
index 00000000000..d9665dfb29e
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-22.c
@@ -0,0 +1,66 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+__attribute__ ((noinline,optimize(0)))
+ee_u16 crcu16_O0 (ee_u16 data, ee_u16 crc) {
+  ee_u8 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 16; i++) {
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+ee_u16 crcu16 (ee_u16 data, ee_u16 crc) {
+  ee_u8 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 16; i++) {
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+int main ()
+{
+  ee_u16 crc = 0x0D80;
+  for (ee_u16 i = 0; i < 255; i++)
+    {
+      ee_u16 res1 = crcu16_O0 (i, crc);
+      ee_u16 res2 = crcu16 (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 15" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-23.c b/gcc/testsuite/gcc.dg/torture/crc-23.c
new file mode 100644
index 00000000000..4b960e64f90
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-23.c
@@ -0,0 +1,74 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -ftree-cselim" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+// Modified example from crc-from-fedora-packages-24.c
+
+#include <stdint.h>
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+void crc_byte_O0 (const char data, uint16_t *crc16)
+{
+  int k;
+  uint16_t c,d ;
+
+  c = data << 8 ;
+  d = c;
+
+  for (k = 0; k < 16; k++) {
+      *crc16 = (c & 0x8000) ^ *crc16;
+
+      if (*crc16 & 0x8000) {
+	  *crc16 = *crc16 << 1;
+	  *crc16 = *crc16 ^ 0x8005;
+	} else
+	*crc16 = *crc16 << 1;
+
+      d = d << 1;
+      c = d;
+    }
+}
+
+void crc_byte (const char data, uint16_t *crc16)
+{
+  int k;
+  uint16_t c,d ;
+
+  c = data << 8 ;
+  d = c;
+
+  for (k = 0; k < 16; k++) {
+      *crc16 = (c & 0x8000) ^ *crc16;
+
+      if (*crc16 & 0x8000) {
+	  *crc16 = *crc16 << 1;
+	  *crc16 = *crc16 ^ 0x8005;
+	} else
+	*crc16 = *crc16 << 1;
+
+      d = d << 1;
+      c = d;
+    }
+}
+
+int main ()
+{
+  uint16_t crc = 0x0D80;
+  for (char i = 0; i < 127; i++)
+    {
+      uint16_t res1 = crc, res2 = crc;
+      crc_byte_O0 (i, &res1);
+      crc_byte (i, &res2);
+
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 15" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-24.c b/gcc/testsuite/gcc.dg/torture/crc-24.c
new file mode 100644
index 00000000000..288536dff7b
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-24.c
@@ -0,0 +1,30 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+// Modified Coremark test, we don't detect.
+
+#include <stdint.h>
+
+uint16_t not_crcu8 (uint16_t data, uint16_t crc)
+{
+  uint16_t i = 0, carry = 0;
+  for (i = 0; i < 16; i++)
+    {
+      if ((((crc & 1) == 1) && ((data & 1) == 0))
+	  || (((crc & 1) == 0) && (data & 1) == 1))
+	{
+	  crc ^= 0x4002;
+	  carry = 1;
+	}
+      else
+	carry = 0;
+      crc >>= 1;
+      data >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-25.c b/gcc/testsuite/gcc.dg/torture/crc-25.c
new file mode 100644
index 00000000000..e41d95e54fa
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-25.c
@@ -0,0 +1,78 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-funroll-loops" "-fpeel-loops" "-flto"} } */
+
+//Test from roms/u-boot-sam460ex/drivers/net/mpc512x_fec.c(fsl_mcdmafec.c)
+
+#include <stdint.h>
+#include <stdlib.h>
+
+typedef uint8_t u8;
+typedef uint32_t u32;
+
+__attribute__ ((noinline,optimize(0)))
+u32 mpc512x_fec_set_hwaddr_O0 (unsigned char *mac)
+{
+  u8 currByte;                    /* byte for which to compute the CRC */
+  int byte;                       /* loop - counter */
+  int bit;                        /* loop - counter */
+  u32 crc = 0xffffffff;           /* initial value */
+
+  for (byte = 0; byte < 6; byte++) {
+      currByte = mac[byte];
+      for (bit = 0; bit < 8; bit++) {
+	  if ((currByte & 0x01) ^ (crc & 0x01)) {
+	      crc >>= 1;
+	      crc = crc ^ 0xedb88320;
+	    } else {
+	      crc >>= 1;
+	    }
+	  currByte >>= 1;
+	}
+    }
+
+  crc = crc >> 26;
+  return crc;
+}
+
+u32 mpc512x_fec_set_hwaddr (unsigned char *mac)
+{
+  u8 currByte;                    /* byte for which to compute the CRC */
+  int byte;                       /* loop - counter */
+  int bit;                        /* loop - counter */
+  u32 crc = 0xffffffff;           /* initial value */
+
+  for (byte = 0; byte < 6; byte++) {
+      currByte = mac[byte];
+      for (bit = 0; bit < 8; bit++) {
+	  if ((currByte & 0x01) ^ (crc & 0x01)) {
+	      crc >>= 1;
+	      crc = crc ^ 0xedb88320;
+	    } else {
+	      crc >>= 1;
+	    }
+	  currByte >>= 1;
+	}
+    }
+
+  crc = crc >> 26;
+  return crc;
+}
+
+int main ()
+{
+  unsigned char st[6] = "Hello";
+  for (unsigned char i = 0; i < 255; i++)
+    {
+      st[0] = i;
+      u32 res1 = mpc512x_fec_set_hwaddr_O0 (st);
+      u32 res2 = mpc512x_fec_set_hwaddr (st);
+      if (res1 != res2)
+	abort ();
+    }
+}
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-26.c b/gcc/testsuite/gcc.dg/torture/crc-26.c
new file mode 100644
index 00000000000..9c54cf08edb
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-26.c
@@ -0,0 +1,55 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-funroll-loops" "-fpeel-loops"  "-flto"} } */
+
+//Test from roms/u-boot-sam460ex/drivers/mtd/ubi/crc32.c
+#include <stdint.h>
+#include <stdlib.h>
+
+typedef uint8_t u8;
+typedef uint32_t u32;
+#define CRCPOLY_LE 0xedb88320
+
+__attribute__ ((noinline,optimize(0)))
+u32 crc32_le_O0 (u32 crc, unsigned char const *p, size_t len)
+{
+  int i;
+  while (len--) {
+      crc ^= *p++;
+      for (i = 0; i < 8; i++)
+	crc = (crc >> 1) ^ ((crc & 1) ? CRCPOLY_LE : 0);
+    }
+  return crc;
+}
+
+u32 crc32_le (u32 crc, unsigned char const *p, size_t len)
+{
+  int i;
+  while (len--) {
+      crc ^= *p++;
+      for (i = 0; i < 8; i++)
+	crc = (crc >> 1) ^ ((crc & 1) ? CRCPOLY_LE : 0);
+    }
+  return crc;
+}
+
+
+int main ()
+{
+  u32 crc = 0x0D800D80;
+  unsigned char st[2] = {'H','i'};
+  for (unsigned char i = 0; i < 255; i++)
+    {
+      st[0] = i;
+      u32 res1 = crc32_le_O0 (crc, st, 2);
+      u32 res2 = crc32_le (crc, st, 2);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-27.c b/gcc/testsuite/gcc.dg/torture/crc-27.c
new file mode 100644
index 00000000000..86f633ee706
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-27.c
@@ -0,0 +1,27 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+// Test from roms/ipxe/src/util/zbin.c
+// We don't detect this case, as second operand of the xor is a variable.
+
+#include <stdint.h>
+#include <stddef.h>
+
+#define CRCPOLY 0xedb88320
+#define CRCSEED 0xffffffff
+
+uint32_t crc32_le ( uint32_t crc, const void *data, size_t len ) {
+  const uint8_t *src = data;
+  uint32_t mult;
+  unsigned int i;
+
+  while ( len-- ) {
+      crc ^= *(src++);
+      for ( i = 0 ; i < 8 ; i++ ) {
+	  mult = ( ( crc & 1 ) ? CRCPOLY : 0 );
+	  crc = ( ( crc >> 1 ) ^ mult );
+	}
+    }
+  return crc;
+}
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-28.c b/gcc/testsuite/gcc.dg/torture/crc-28.c
new file mode 100644
index 00000000000..e549f279926
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-28.c
@@ -0,0 +1,90 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-funroll-loops" "-fpeel-loops" "-flto"} } */
+
+// Test from roms/u-boot/drivers/ram/octeon/dimm_spd_eeprom.c
+
+#include <stdint.h>
+#include <stdlib.h>
+
+typedef uint8_t u8;
+typedef uint16_t u16;
+
+// We don't verify as crc is of type int (32 bit),
+// but the polynomial fits into 16 bit.
+u16 ddr3_crc16_orig (u8 *ptr, int count)
+{
+  /* From DDR3 SPD specification */
+  int crc, i;
+
+  crc = 0;
+  while (--count >= 0) {
+      crc = crc ^ (int)*ptr++ << 8;
+      for (i = 0; i < 8; ++i) {
+	  if (crc & 0x8000)
+	    crc = crc << 1 ^ 0x1021;
+	  else
+	    crc = crc << 1;
+	}
+    }
+
+  return (crc & 0xFFFF);
+}
+
+__attribute__ ((noinline,optimize(0)))
+u16 ddr3_crc16_modified_O0  (u8 *ptr, int count)
+{
+  /* From DDR3 SPD specification */
+  u16 crc, i;
+
+  crc = 0;
+  while (--count >= 0) {
+      crc = crc ^ (int)*ptr++ << 8;
+      for (i = 0; i < 8; ++i) {
+	  if (crc & 0x8000)
+	    crc = crc << 1 ^ 0x1021;
+	  else
+	    crc = crc << 1;
+	}
+    }
+
+  return (crc & 0xFFFF);
+}
+
+u16 ddr3_crc16_modified  (u8 *ptr, int count)
+{
+  /* From DDR3 SPD specification */
+  u16 crc, i;
+
+  crc = 0;
+  while (--count >= 0) {
+      crc = crc ^ (int)*ptr++ << 8;
+      for (i = 0; i < 8; ++i) {
+	  if (crc & 0x8000)
+	    crc = crc << 1 ^ 0x1021;
+	  else
+	    crc = crc << 1;
+	}
+    }
+
+  return (crc & 0xFFFF);
+}
+
+int main ()
+{
+  u8 st[2] = {'H', 'i'};
+  for (u8 i = 0; i < 255; i++)
+    {
+      st[0] = i;
+      u16 res1 = ddr3_crc16_modified_O0 (st, 2);
+      u16 res2 = ddr3_crc16_modified (st, 2);
+      if (res1 != res2)
+	abort ();
+    }
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-29.c b/gcc/testsuite/gcc.dg/torture/crc-29.c
new file mode 100644
index 00000000000..86bb681c0ce
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-29.c
@@ -0,0 +1,31 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+/* This is a CRC, even though it may seem it's not.
+   'j' is initialized with 4 (100) and increased by 2 each time.
+   Thus, first bit value is never 1. For each iteration 'j & 1' yields 0,
+   and it doesn't affect the CRC result.  */
+
+#include <stdint.h>
+
+uint16_t crc (uint8_t data, uint16_t crc) {
+  uint8_t x16 = 0, carry = 0;
+  for (uint8_t i = 0, j=4; i < 8; i++, j+=2) {
+      x16 = (uint8_t) (((uint8_t) crc & 1)  ^ (j & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-3.c b/gcc/testsuite/gcc.dg/torture/crc-3.c
new file mode 100644
index 00000000000..1ea4e434ddf
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-3.c
@@ -0,0 +1,36 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+//We don't verify this case as for the CRC unsigned int (32 bit) is used and
+// the polynomial fits into 16 bit.
+
+unsigned short crc16 (char *data_p, unsigned short length) {
+    unsigned char i;
+    unsigned int data;
+    unsigned int crc = 0xffff;
+
+    if (length == 0)
+        return (~crc);
+
+    do {
+        for (i = 0, data = (unsigned int) 0xff & *data_p++;
+             i < 8;
+             i++, data >>= 1) {
+            if ((crc & 0x0001) ^ (data & 0x0001))
+                crc = (crc >> 1) ^ 0x8408;
+            else crc >>= 1;
+        }
+    } while (--length);
+
+    crc = ~crc;
+    data = crc;
+    crc = (crc << 8) | (data >> 8 & 0xff);
+
+    return (crc);
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{\[0, \]*1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0\\\}" "crc" } } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-4.c b/gcc/testsuite/gcc.dg/torture/crc-4.c
new file mode 100644
index 00000000000..94ea0206c24
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-4.c
@@ -0,0 +1,51 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+uint16_t crc16_update_O0 (uint16_t crc, uint8_t a) {
+    int i;
+    crc ^= a;
+    for (i = 0; i < 8; ++i) {
+        if (crc & 1)
+            crc = (crc >> 1) ^ 0xA001;
+        else
+            crc = (crc >> 1);
+    }
+    return crc;
+}
+
+uint16_t crc16_update (uint16_t crc, uint8_t a) {
+    int i;
+    crc ^= a;
+    for (i = 0; i < 8; ++i) {
+        if (crc & 1)
+            crc = (crc >> 1) ^ 0xA001;
+        else
+            crc = (crc >> 1);
+    }
+    return crc;
+}
+
+int main ()
+{
+  uint16_t crc = 0x0D80;
+  for (uint8_t i = 0; i < 255; i++)
+    {
+      uint16_t res1 = crc16_update (crc, i);
+      uint16_t res2 = crc16_update_O0 (crc, i);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1\\\}" "crc" } } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-5.c b/gcc/testsuite/gcc.dg/torture/crc-5.c
new file mode 100644
index 00000000000..7f095d59405
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-5.c
@@ -0,0 +1,66 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+__attribute__ ((noinline,optimize(0)))
+ee_u16 crcu8_O0 (ee_u8 data, ee_u16 crc) {
+  ee_u8 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+  ee_u8 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+int main ()
+{
+  ee_u16 crc = 0x0D80;
+  for (ee_u8 i = 0; i < 255; i++)
+    {
+      ee_u16 res1 = crcu8_O0 (i, crc);
+      ee_u16 res2 = crcu8 (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+/* { dg-final { scan-tree-dump "crcu8 function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{\[0, \]*1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1\\\}" "crc" } } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-6.c b/gcc/testsuite/gcc.dg/torture/crc-6.c
new file mode 100644
index 00000000000..a3705d683bc
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-6.c
@@ -0,0 +1,64 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+typedef uint8_t crc;
+#define WIDTH (8 * sizeof(crc))
+#define TOPBIT (1 << (WIDTH - 1))
+
+__attribute__ ((noinline,optimize(0)))
+crc crcSlow_O0 (uint8_t const message[], int nBytes) {
+    crc remainder = 0;
+/*
+* Perform modulo-2 division, a byte at a time.
+*/
+    for (int byte = 0; byte < nBytes; ++byte) {
+        remainder ^= (message[byte] << (WIDTH - 8));
+        for (uint8_t bit = 8; bit > 0; --bit) {
+            if (remainder & TOPBIT) {
+                remainder = (remainder << 1) ^ 1234;
+            } else {
+                remainder = (remainder << 1);
+            }
+        }
+    }
+    return (remainder);
+}
+
+crc crcSlow (uint8_t const message[], int nBytes) {
+  crc remainder = 0;
+/*
+* Perform modulo-2 division, a byte at a time.
+*/
+  for (int byte = 0; byte < nBytes; ++byte) {
+      remainder ^= (message[byte] << (WIDTH - 8));
+      for (uint8_t bit = 8; bit > 0; --bit) {
+	  if (remainder & TOPBIT) {
+	      remainder = (remainder << 1) ^ 1234;
+	    } else {
+	      remainder = (remainder << 1);
+	    }
+	}
+    }
+  return (remainder);
+}
+
+int main ()
+{
+  for (crc i = 0; i < 255; i++)
+    {
+      crc res1 = crcSlow_O0 (&i, 1);
+      crc res2 = crcSlow (&i, 1);
+      if (res1 != res2)
+	abort ();
+    }
+}
+/* { dg-final { scan-tree-dump "crcSlow function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{1, 1, 0, 1, 0, 0, 1, 0\\\}" "crc" } } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-7.c b/gcc/testsuite/gcc.dg/torture/crc-7.c
new file mode 100644
index 00000000000..53d88cb3310
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-7.c
@@ -0,0 +1,50 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+uint16_t crc_xmodem_update_O0 (uint16_t crc, uint8_t data) {
+    int i;
+    crc = crc ^ ((uint16_t) data << 8);
+    for (i = 0; i < 8; i++) {
+        if (crc & 0x8000)
+            crc = (crc << 1) ^ 0x1021;
+        else
+            crc <<= 1;
+    }
+    return crc;
+}
+
+uint16_t crc_xmodem_update (uint16_t crc, uint8_t data) {
+    int i;
+    crc = crc ^ ((uint16_t) data << 8);
+    for (i = 0; i < 8; i++) {
+        if (crc & 0x8000)
+            crc = (crc << 1) ^ 0x1021;
+        else
+            crc <<= 1;
+    }
+    return crc;
+}
+
+int main ()
+{
+  uint16_t crc = 0x0D80;
+  for (uint8_t i = 0; i < 255; i++)
+    {
+      uint16_t res1 = crc_xmodem_update_O0 (i, crc);
+      uint16_t res2 = crc_xmodem_update (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+/* { dg-final { scan-tree-dump "crc_xmodem_update function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1\\\}" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-8.c b/gcc/testsuite/gcc.dg/torture/crc-8.c
new file mode 100644
index 00000000000..41f8f5797d5
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-8.c
@@ -0,0 +1,50 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+uint8_t _crc_ibutton_update_O0 (uint8_t crc, uint8_t data) {
+    uint8_t i;
+    crc = crc ^ data;
+    for (i = 0; i < 8; i++) {
+        if (crc & 0x01)
+            crc = (crc >> 1) ^ 0x8C;
+        else
+            crc >>= 1;
+    }
+    return crc;
+}
+
+uint8_t _crc_ibutton_update (uint8_t crc, uint8_t data) {
+    uint8_t i;
+    crc = crc ^ data;
+    for (i = 0; i < 8; i++) {
+        if (crc & 0x01)
+            crc = (crc >> 1) ^ 0x8C;
+        else
+            crc >>= 1;
+    }
+    return crc;
+}
+
+int main ()
+{
+  uint8_t crc = 0x0D;
+  for (uint8_t i = 0; i < 255; i++)
+    {
+      uint8_t res1 = _crc_ibutton_update_O0 (i, crc);
+      uint8_t res2 = _crc_ibutton_update (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+/* { dg-final { scan-tree-dump "_crc_ibutton_update function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{\[0, \]*1, 0, 0, 0, 1, 1, 0, 0\\\}" "crc" } } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-9.c b/gcc/testsuite/gcc.dg/torture/crc-9.c
new file mode 100644
index 00000000000..af7386b1bd8
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-9.c
@@ -0,0 +1,56 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+#include <stdlib.h>
+
+typedef unsigned char uint8_t;
+
+__attribute__ ((noinline,optimize(0)))
+uint8_t gencrc_O0 (uint8_t *data, size_t len) {
+    uint8_t crc = 0xff;
+    size_t i, j;
+    for (i = 0; i < len; i++) {
+        crc ^= data[i];
+        for (j = 0; j < 8; j++) {
+            if ((crc & 0x80) != 0)
+                crc = (uint8_t) ((crc << 1) ^ 0x31);
+            else
+                crc <<= 1;
+        }
+    }
+    return crc;
+}
+
+uint8_t gencrc (uint8_t *data, size_t len) {
+    uint8_t crc = 0xff;
+    size_t i, j;
+    for (i = 0; i < len; i++) {
+        crc ^= data[i];
+        for (j = 0; j < 8; j++) {
+            if ((crc & 0x80) != 0)
+                crc = (uint8_t) ((crc << 1) ^ 0x31);
+            else
+                crc <<= 1;
+        }
+    }
+    return crc;
+}
+
+int main ()
+{
+  for (uint8_t i = 0; i < 255; i++)
+    {
+      uint8_t res1 = gencrc_O0 (&i, 1);
+      uint8_t res2 = gencrc (&i, 1);
+      if (res1 != res2)
+	abort ();
+    }
+}
+
+/* { dg-final { scan-tree-dump "gencrc function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{\[0, \]*0, 0, 1, 1, 0, 0, 0, 1\\\}" "crc" } } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-CCIT-data16-xorOutside_InsideFor.c b/gcc/testsuite/gcc.dg/torture/crc-CCIT-data16-xorOutside_InsideFor.c
new file mode 100644
index 00000000000..c0c5f70ac35
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-CCIT-data16-xorOutside_InsideFor.c
@@ -0,0 +1,58 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+#include <stdint.h>
+
+__attribute__ ((noinline))
+uint16_t crc16_xor_outside (uint16_t data, uint16_t crc)
+{
+  int carry;
+  crc ^= data;
+  for (int i = 0; i < 16; ++i) {
+      carry = ((crc & 0x8000));
+      crc <<= 1;
+      if (carry) crc ^= 0x1021;
+    }
+  return crc;
+}
+
+__attribute__ ((noinline))
+uint16_t crc16_xor_inside (uint16_t data, uint16_t crc)
+{
+  int carry;
+  for (int i = 0; i < 16; ++i) {
+      carry = ((crc & 0x8000) ^ (data & 0x8000));
+      crc <<= 1;
+      data <<= 1;
+      if (carry) crc ^= 0x1021;
+    }
+  return crc;
+}
+
+int main ()
+{
+  uint16_t crc = 0;
+
+  for (uint16_t i = 0; i < 655; i++)
+    {
+      uint16_t res1 = crc16_xor_outside (i, crc);
+      uint16_t res2 = crc16_xor_inside (i, crc);
+      crc = res1;
+      if (res1 != res2)
+	abort ();
+    }
+
+  if (crc16_xor_outside (0x1111, 0xFFFF) != 0x2f5d)
+    abort ();
+
+  if (crc16_xor_inside (0x1111, 0xFFFF) != 0x2f5d)
+    abort ();
+}
+
+/* { dg-final { scan-tree-dump "crc16_xor_outside function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "crc16_xor_inside function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 15" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 2 "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-CCIT-data16.c b/gcc/testsuite/gcc.dg/torture/crc-CCIT-data16.c
new file mode 100644
index 00000000000..c2f564279c8
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-CCIT-data16.c
@@ -0,0 +1,51 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+#include <stdint.h>
+
+__attribute__ ((noinline,optimize(0)))
+uint16_t crc16_O0 (uint16_t data, uint16_t crc)
+{
+  int carry;
+  for (int i = 0; i < 16; ++i) {
+      carry = ((crc & 0x8000) ^ (data & 0x8000));
+      crc <<= 1;
+      data <<= 1;
+      if (carry) crc ^= 0x1021;
+    }
+  return crc;
+}
+
+uint16_t crc16 (uint16_t data, uint16_t crc)
+{
+  int carry;
+  for (int i = 0; i < 16; ++i) {
+      carry = ((crc & 0x8000) ^ (data & 0x8000));
+      crc <<= 1;
+      data <<= 1;
+      if (carry) crc ^= 0x1021;
+    }
+  return crc;
+}
+
+int main ()
+{
+  uint16_t crc = 0;
+
+  for (uint16_t i = 0; i < 655; i++)
+    {
+      uint16_t res1 = crc16_O0 (i, crc);
+      uint16_t res2 = crc16 (i, crc);
+      crc = res1;
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+
+/* { dg-final { scan-tree-dump "crc16 function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 15" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-CCIT-data8.c b/gcc/testsuite/gcc.dg/torture/crc-CCIT-data8.c
new file mode 100644
index 00000000000..a9a8148d330
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-CCIT-data8.c
@@ -0,0 +1,47 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+uint16_t crc16_O0 (uint8_t data, uint16_t crc) {
+  int carry;
+  for (int i = 0; i < 8; ++i) {
+      carry = ((crc & 0x8000) >> 8 ^ (data & 0x80));
+      crc <<= 1;
+      data <<= 1;
+      if (carry) crc ^= 0x1021;
+    }
+  return crc;
+}
+
+uint16_t crc16 (uint8_t data, uint16_t crc) {
+  int carry;
+  for (int i = 0; i < 8; ++i) {
+      carry = ((crc & 0x8000) >> 8 ^ (data & 0x80));
+      crc <<= 1;
+      data <<= 1;
+      if (carry) crc ^= 0x1021;
+    }
+  return crc;
+}
+
+int main ()
+{
+  uint16_t crc = 0x0D80;
+  for (uint8_t i = 0; i < 255; i++)
+    {
+      uint16_t res1 = crc16_O0 (i, crc);
+      uint16_t res2 = crc16 (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+
+/* { dg-final { scan-tree-dump "crc16 function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-coremark16-data16.c b/gcc/testsuite/gcc.dg/torture/crc-coremark16-data16.c
new file mode 100644
index 00000000000..7a1cee67244
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-coremark16-data16.c
@@ -0,0 +1,65 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+__attribute__ ((noinline,optimize(0)))
+ee_u16 crcu16_O0 (ee_u16 data, ee_u16 crc) {
+  ee_u8 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 16; i++) {
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+ee_u16 crcu16 (ee_u16 data, ee_u16 crc) {
+  ee_u8 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 16; i++) {
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+int main ()
+{
+  ee_u16 crc = 0x0D80;
+  for (ee_u16 i = 0; i < 65535; i++)
+    {
+      ee_u16 res1 = crcu16_O0 (i, crc);
+      ee_u16 res2 = crcu16 (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 15" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{\[0, \]*1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1\\\}" "crc" } } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-coremark32-data16.c b/gcc/testsuite/gcc.dg/torture/crc-coremark32-data16.c
new file mode 100644
index 00000000000..0675cdc1b36
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-coremark32-data16.c
@@ -0,0 +1,64 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+
+typedef unsigned int ee_u32;
+typedef unsigned short ee_u16;
+
+__attribute__ ((noinline,optimize(0)))
+ee_u32 crcu32_O0 (ee_u16 data, ee_u32 crc) {
+  ee_u32 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 16; i++) {
+      x16 = ((data & 1) ^ (crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002123;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x80000000;
+      else
+	crc &= 0x7fffffff;
+    }
+  return crc;
+}
+
+ee_u32 crcu32 (ee_u16 data, ee_u32 crc) {
+  ee_u32 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 16; i++) {
+      x16 = ((data & 1) ^ (crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002123;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x80000000;
+      else
+	crc &= 0x7fffffff;
+    }
+  return crc;
+}
+
+int main ()
+{
+  ee_u32 crc = 0;
+  for (ee_u16 i = 0; i < 0xff; i++)
+    {
+      ee_u32 res1 = crcu32_O0 (i, crc);
+      ee_u32 res2 = crcu32 (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 15" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-coremark32-data32.c b/gcc/testsuite/gcc.dg/torture/crc-coremark32-data32.c
new file mode 100644
index 00000000000..f9bd1952ba5
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-coremark32-data32.c
@@ -0,0 +1,63 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+
+typedef unsigned int ee_u32;
+
+__attribute__ ((noinline,optimize(0)))
+ee_u32 crcu32_O0 (ee_u32 data, ee_u32 crc) {
+  ee_u32 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 32; i++) {
+      x16 = ((data & 1) ^ (crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002123;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x80000000;
+      else
+	crc &= 0x7fffffff;
+    }
+  return crc;
+}
+
+ee_u32 crcu32 (ee_u32 data, ee_u32 crc) {
+  ee_u32 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 32; i++) {
+      x16 = ((data & 1) ^ (crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002123;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x80000000;
+      else
+	crc &= 0x7fffffff;
+    }
+  return crc;
+}
+
+int main ()
+{
+  ee_u32 crc = 0;
+  for (ee_u32 i = 0; i < 0xff; i++)
+    {
+      ee_u32 res1 = crcu32_O0 (i, crc);
+      ee_u32 res2 = crcu32 (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 31" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-coremark32-data8.c b/gcc/testsuite/gcc.dg/torture/crc-coremark32-data8.c
new file mode 100644
index 00000000000..b998524e595
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-coremark32-data8.c
@@ -0,0 +1,64 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+
+typedef unsigned int ee_u32;
+typedef unsigned char ee_u8;
+
+__attribute__ ((noinline,optimize(0)))
+ee_u32 crcu32_O0 (ee_u8 data, ee_u32 crc) {
+  ee_u32 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      x16 = ((data & 1) ^ (crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002123;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x80000000;
+      else
+	crc &= 0x7fffffff;
+    }
+  return crc;
+}
+
+ee_u32 crcu32 (ee_u8 data, ee_u32 crc) {
+  ee_u32 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      x16 = ((data & 1) ^ (crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002123;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x80000000;
+      else
+	crc &= 0x7fffffff;
+    }
+  return crc;
+}
+
+int main ()
+{
+  ee_u32 crc = 0;
+  for (ee_u8 i = 0; i < 0xff; i++)
+    {
+      ee_u32 res1 = crcu32_O0 (i, crc);
+      ee_u32 res2 = crcu32 (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-coremark64-data64.c b/gcc/testsuite/gcc.dg/torture/crc-coremark64-data64.c
new file mode 100644
index 00000000000..e57e82813cf
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-coremark64-data64.c
@@ -0,0 +1,63 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+
+typedef unsigned long long int ee_u64;
+
+__attribute__ ((noinline,optimize(0)))
+ee_u64 crcu64_O0 (ee_u64 data, ee_u64 crc) {
+  ee_u64 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 64; i++) {
+      x16 = ((data & 1) ^ (crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002123f4002123f;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000000000000000;
+      else
+	crc &= 0x7fffffffffffffff;
+    }
+  return crc;
+}
+
+ee_u64 crcu64 (ee_u64 data, ee_u64 crc) {
+  ee_u64 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 64; i++) {
+      x16 = ((data & 1) ^ (crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002123f4002123f;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000000000000000;
+      else
+	crc &= 0x7fffffffffffffff;
+    }
+  return crc;
+}
+
+int main ()
+{
+  ee_u64 crc = 0;
+  for (ee_u64 i = 0; i < 0xff; i++)
+    {
+      ee_u64 res1 = crcu64_O0 (i, crc);
+      ee_u64 res2 = crcu64 (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 63" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-coremark8-data8.c b/gcc/testsuite/gcc.dg/torture/crc-coremark8-data8.c
new file mode 100644
index 00000000000..b16c720bb58
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-coremark8-data8.c
@@ -0,0 +1,63 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdlib.h>
+
+typedef unsigned char ee_u8;
+
+__attribute__ ((noinline,optimize(0)))
+ee_u8 crcu8_O0(ee_u8 data, ee_u8 crc) {
+  ee_u8 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      x16 = ((data & 1) ^ (crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x40;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x80;
+      else
+	crc &= 0x7f;
+    }
+  return crc;
+}
+
+ee_u8 crcu8(ee_u8 data, ee_u8 crc) {
+  ee_u8 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      x16 = ((data & 1) ^ (crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x40;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x80;
+      else
+	crc &= 0x7f;
+    }
+  return crc;
+}
+
+int main ()
+{
+  ee_u8 crc = 0;
+  for (ee_u8 i = 0; i < 0xff; i++)
+    {
+      ee_u8 res1 = crcu8_O0 (i, crc);
+      ee_u8 res2 = crcu8 (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-crc32-data16.c b/gcc/testsuite/gcc.dg/torture/crc-crc32-data16.c
new file mode 100644
index 00000000000..f6d4725ce80
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-crc32-data16.c
@@ -0,0 +1,51 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+uint32_t _crc32_O0 (uint16_t data, uint32_t crc) {
+  int i;
+  for (i = 0; i < 16; i++) {
+      if ((crc & 0x80000000) >> 16 ^ (data & 0x8000))
+	crc = (crc << 1) ^ 0x04C11DB7;
+      else
+	crc = (crc << 1);
+      data <<= 1;
+    }
+  return crc;
+}
+
+uint32_t _crc32 (uint16_t data, uint32_t crc) {
+  int i;
+  for (i = 0; i < 16; i++) {
+      if ((crc & 0x80000000) >> 16 ^ (data & 0x8000))
+	crc = (crc << 1) ^ 0x04C11DB7;
+      else
+	crc = (crc << 1);
+      data <<= 1;
+    }
+  return crc;
+}
+
+int main ()
+{
+  uint32_t crc = 0;
+
+  for (uint16_t i = 0; i < 0xff; i++)
+    {
+      uint32_t res1 = _crc32_O0 (i, crc);
+      uint32_t res2 = _crc32 (i, crc);
+      crc = res2;
+      if (res1 != res2)
+	abort ();
+    }
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 15" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC." "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-crc32-data24.c b/gcc/testsuite/gcc.dg/torture/crc-crc32-data24.c
new file mode 100644
index 00000000000..4d3afa26c38
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-crc32-data24.c
@@ -0,0 +1,20 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+uint32_t _crc32 (uint32_t data, uint32_t crc) {
+  int i;
+  for (i = 0; i < 24; i++) {
+      if ((crc & 0x80000000) >> 8 ^ (data & 0x800000))
+	crc = (crc << 1) ^ 0x04C11DB7;
+      else
+	crc = (crc << 1);
+      data <<= 1;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump "_crc32 function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 23" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-crc32-data8.c b/gcc/testsuite/gcc.dg/torture/crc-crc32-data8.c
new file mode 100644
index 00000000000..94ca7f2c114
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-crc32-data8.c
@@ -0,0 +1,51 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+uint32_t _crc32_O0 (uint8_t data, uint32_t crc) {
+  int i;
+  for (i = 0; i < 8; i++) {
+      if ((crc & 0x80000000) >> 24 ^ (data & 0x80))
+	crc = (crc << 1) ^ 0x04C11DB7;
+      else
+	crc = (crc << 1);
+      data <<= 1;
+    }
+  return crc;
+}
+
+uint32_t _crc32 (uint8_t data, uint32_t crc) {
+  int i;
+  for (i = 0; i < 8; i++) {
+      if ((crc & 0x80000000) >> 24 ^ (data & 0x80))
+	crc = (crc << 1) ^ 0x04C11DB7;
+      else
+	crc = (crc << 1);
+      data <<= 1;
+    }
+  return crc;
+}
+
+int main ()
+{
+  uint32_t crc = 0;
+
+  for (uint8_t i = 0; i < 0xff; i++)
+    {
+      uint32_t res1 = _crc32_O0 (i, crc);
+      uint32_t res2 = _crc32 (i, crc);
+      crc = res2;
+      if (res1 != res2)
+	abort ();
+    }
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC." "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-crc32.c b/gcc/testsuite/gcc.dg/torture/crc-crc32.c
new file mode 100644
index 00000000000..dc936ba5136
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-crc32.c
@@ -0,0 +1,51 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+uint32_t _crc32_O0 (uint32_t data, uint32_t crc) {
+  int i;
+  for (i = 0; i < 32; i++) {
+      if ((crc & 0x80000000) ^ (data & 0x80000000))
+	crc = (crc << 1) ^ 0x04C11DB7;
+      else
+	crc = (crc << 1);
+      data <<= 1;
+    }
+  return crc;
+}
+
+uint32_t _crc32 (uint32_t data, uint32_t crc) {
+  int i;
+  for (i = 0; i < 32; i++) {
+      if ((crc & 0x80000000) ^ (data & 0x80000000))
+	crc = (crc << 1) ^ 0x04C11DB7;
+      else
+	crc = (crc << 1);
+      data <<= 1;
+    }
+  return crc;
+}
+
+int main ()
+{
+  uint32_t crc = 0;
+
+  for (uint32_t i = 0; i < 0xffff; i++)
+    {
+      uint32_t res1 = _crc32_O0 (i, crc);
+      uint32_t res2 = _crc32 (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res2;
+    }
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 31" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC." "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-crc64-data32.c b/gcc/testsuite/gcc.dg/torture/crc-crc64-data32.c
new file mode 100644
index 00000000000..59d853c159f
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-crc64-data32.c
@@ -0,0 +1,52 @@ 
+/* { dg-do run { target lp64 } } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+// CRC64_ECMA_182
+__attribute__ ((noinline,optimize(0)))
+uint64_t _crc64_O0 (uint32_t data, uint64_t crc) {
+  int i;
+  for (i = 0; i < 32; i++) {
+      if (((crc & 0x8000000000000000) >> 32 ^ (data & 0x80000000)))
+	crc = (crc << 1) ^ 0x42F0E1EBA9EA3693;
+      else
+	crc = (crc << 1);
+      data <<= 1;
+    }
+  return crc;
+}
+
+uint64_t _crc64 (uint32_t data, uint64_t crc) {
+  int i;
+  for (i = 0; i < 32; i++) {
+      if (((crc & 0x8000000000000000) >> 32 ^ (data & 0x80000000)))
+	crc = (crc << 1) ^ 0x42F0E1EBA9EA3693;
+      else
+	crc = (crc << 1);
+      data <<= 1;
+    }
+  return crc;
+}
+
+int main ()
+{
+  uint64_t crc = 0;
+
+  for (uint32_t i = 0; i < 0xff; i++)
+    {
+      uint64_t res1 = _crc64_O0 (i, crc);
+      uint64_t res2 = _crc64 (i, crc);
+      crc = res2;
+      if (res1 != res2)
+	abort ();
+    }
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 31" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-crc64-data64.c b/gcc/testsuite/gcc.dg/torture/crc-crc64-data64.c
new file mode 100644
index 00000000000..cbf8228a910
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-crc64-data64.c
@@ -0,0 +1,52 @@ 
+/* { dg-do run { target lp64 } } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+// CRC64_ECMA_182
+__attribute__ ((noinline,optimize(0)))
+uint64_t _crc64_O0 (uint64_t crc, uint64_t data) {
+  int i;
+  for (i = 0; i < 64; i++) {
+      if (((crc & 0x8000000000000000) ^ (data & 0x8000000000000000)))
+	crc = (crc << 1) ^ 0x42F0E1EBA9EA3693;
+      else
+	crc = (crc << 1);
+      data <<= 1;
+    }
+  return crc;
+}
+
+uint64_t _crc64 (uint64_t crc, uint64_t data) {
+  int i;
+  for (i = 0; i < 64; i++) {
+      if (((crc & 0x8000000000000000) ^ (data & 0x8000000000000000)))
+	crc = (crc << 1) ^ 0x42F0E1EBA9EA3693;
+      else
+	crc = (crc << 1);
+      data <<= 1;
+    }
+  return crc;
+}
+
+int main ()
+{
+  uint64_t crc = 0;
+
+  for (uint64_t i = 0; i < 0xff; i++)
+    {
+      uint64_t res1 = _crc64_O0 (i, crc);
+      uint64_t res2 = _crc64 (i, crc);
+      crc = res2;
+      if (res1 != res2)
+	abort ();
+    }
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 63" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-crc8-data8-loop-xorInFor.c b/gcc/testsuite/gcc.dg/torture/crc-crc8-data8-loop-xorInFor.c
new file mode 100644
index 00000000000..8f023d37fa8
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-crc8-data8-loop-xorInFor.c
@@ -0,0 +1,33 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-funroll-loops" "-fpeel-loops" "-flto"} } */
+
+#include <stddef.h>
+#include <assert.h>
+
+typedef unsigned char uint8_t;
+
+uint8_t gencrc (uint8_t *message, size_t len) {
+  uint8_t crc = 0;
+  size_t i, j;
+  for (i = 0; i < len; i++) {
+      uint8_t data = message[i];
+      for (j = 0; j < 8; j++) {
+	  if (((crc & 0x80) ^ (data & 0x80)) != 0)
+	    crc = (uint8_t) ((crc << 1) ^ 0x31);
+	  else
+	    crc <<= 1;
+	  data <<=1;
+	}
+    }
+  return crc;
+}
+
+int main()
+{
+  uint8_t message[] = "Hello world!";
+  assert (gencrc(message, 12) == 0x24);
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-crc8-data8-loop-xorOutsideFor.c b/gcc/testsuite/gcc.dg/torture/crc-crc8-data8-loop-xorOutsideFor.c
new file mode 100644
index 00000000000..12a7d67ea6f
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-crc8-data8-loop-xorOutsideFor.c
@@ -0,0 +1,33 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-funroll-loops" "-fpeel-loops" "-flto"} } */
+
+#include <stddef.h>
+#include <assert.h>
+
+typedef unsigned char uint8_t;
+
+uint8_t gencrc (uint8_t *message, size_t len) {
+  uint8_t crc = 0;
+  size_t i, j;
+  for (i = 0; i < len; i++) {
+      uint8_t data = message[i];
+      crc ^= data;
+      for (j = 0; j < 8; j++) {
+	  if ((crc & 0x80)!= 0)
+	    crc = (uint8_t) ((crc << 1) ^ 0x31);
+	  else
+	    crc <<= 1;
+	}
+    }
+  return crc;
+}
+
+int main()
+{
+  uint8_t message[] = "Hello world!";
+  assert (gencrc(message, 12) == 0x24);
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-crc8-data8-xorOustideFor.c b/gcc/testsuite/gcc.dg/torture/crc-crc8-data8-xorOustideFor.c
new file mode 100644
index 00000000000..e3f9f69302b
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-crc8-data8-xorOustideFor.c
@@ -0,0 +1,51 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+uint8_t gencrc_O0 (uint8_t crc, uint8_t data)
+{
+  size_t j;
+  crc ^= data;
+  for (j = 0; j < 8; j++)
+    {
+      if ((crc & 0x80) != 0)
+	crc = (uint8_t) ((crc << 1) ^ 0x31);
+      else
+	crc <<= 1;
+    }
+  return crc;
+}
+
+uint8_t gencrc (uint8_t crc, uint8_t data)
+{
+  size_t j;
+  crc ^= data;
+  for (j = 0; j < 8; j++)
+    {
+      if ((crc & 0x80) != 0)
+	crc = (uint8_t) ((crc << 1) ^ 0x31);
+      else
+	crc <<= 1;
+    }
+  return crc;
+}
+
+int main ()
+{
+  uint8_t crc = 0x0D;
+  for (uint8_t i = 0; i < 255; i++)
+    {
+      uint8_t res1 = gencrc_O0 (crc, i);
+      uint8_t res2 = gencrc (crc, i);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump-times "Couldn't generate faster CRC code." 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-crc8.c b/gcc/testsuite/gcc.dg/torture/crc-crc8.c
new file mode 100644
index 00000000000..73afe73e635
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-crc8.c
@@ -0,0 +1,49 @@ 
+/* { dg-do run } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-g" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdlib.h>
+
+__attribute__ ((noinline,optimize(0)))
+uint8_t crc8_O0 (uint8_t data, uint8_t crc)
+{
+  int carry;
+  for (int i = 0; i < 8; ++i) {
+      carry = ((crc & 0x80) ^ (data & 0x80));
+      crc <<= 1;
+      data <<= 1;
+      if (carry) crc ^= 0x21;
+    }
+  return crc;
+}
+
+uint8_t crc8 (uint8_t data, uint8_t crc)
+{
+  int carry;
+  for (int i = 0; i < 8; ++i) {
+      carry = ((crc & 0x80) ^ (data & 0x80));
+      crc <<= 1;
+      data <<= 1;
+      if (carry) crc ^= 0x21;
+    }
+  return crc;
+}
+
+int main ()
+{
+  uint8_t crc = 0x0D;
+  for (uint8_t i = 0; i < 255; i++)
+    {
+      uint8_t res1 = crc8_O0 (i, crc);
+      uint8_t res2 = crc8 (i, crc);
+      if (res1 != res2)
+	abort ();
+      crc = res1;
+    }
+}
+
+/* { dg-final { scan-tree-dump "function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit forward" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-1.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-1.c
new file mode 100644
index 00000000000..866c78df55b
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-1.c
@@ -0,0 +1,28 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+// File_Ac3.cpp.ii
+// We don't support non-constant polynomials.
+
+#include <stddef.h>
+typedef unsigned short int16u;
+typedef unsigned char int8u;
+int CRC16_Init(int16u *Table, int16u Polynomial)
+{
+    for (size_t Pos=0; Pos<256; Pos++)
+    {
+        Table[Pos]=(int16u)Pos<<8;
+
+        for(int8u bit=0; bit<8; bit++)
+        {
+            if (Table[Pos]&0x8000)
+                Table[Pos]=(Table[Pos]<<1)^Polynomial;
+            else
+                Table[Pos]=Table[Pos]<<1;
+        }
+    }
+    return 0;
+}
+
+/* { dg-final { scan-tree-dump "Second operand of the xor statement isn't an integer constant.\n" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-10.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-10.c
new file mode 100644
index 00000000000..471e86ba4e5
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-10.c
@@ -0,0 +1,27 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+// File - protocol
+#include <stdint.h>
+#include <stddef.h>
+uint16_t crc16_mcrf4xx(uint16_t crc, uint8_t *data, size_t len) {
+    int i;
+
+    if (!data || !len)
+        return crc;
+
+    while (len--) {
+        crc ^= *data++;
+        for (i = 0; i < 8; i++) {
+            if (crc & 1)
+                crc = (crc >> 1) ^ 0x8408;
+            else
+                crc = (crc >> 1);
+        }
+    }
+
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-11.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-11.c
new file mode 100644
index 00000000000..c3e6d64278b
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-11.c
@@ -0,0 +1,32 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+// File - slz
+#include <stdint.h>
+#include <stdio.h>
+uint32_t crc32_fast[4][256];
+void __slz_make_crc_table(void) {
+    uint32_t c;
+    int n, k;
+
+    for (n = 0; n < 256; n++) {
+        c = (uint32_t) n ^ 255;
+        for (k = 0; k < 8; k++) {
+            if (c & 1) {
+                c = 0xedb88320 ^ (c >> 1);
+            } else {
+                c = c >> 1;
+            }
+        }
+        crc32_fast[0][n] = c ^ 0xff000000;
+    }
+}
+
+int main ()
+{
+    __slz_make_crc_table();
+    printf ("%d", crc32_fast[0][0]);
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-12.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-12.c
new file mode 100644
index 00000000000..8127d87dec5
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-12.c
@@ -0,0 +1,75 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+// File - wifi.  Sizeof check is added for the test.
+
+#include <stdlib.h>
+#include <stdbool.h>
+#include <stdio.h>
+typedef unsigned int u32;
+typedef unsigned char u8;
+u32 WIFI_CRC32Table[256];
+bool initialized;
+u32 reflect (u32 ref, char ch)
+{
+  if (sizeof (u32) < 4)
+    exit (0);
+
+  u32 value = 0;
+
+  for (int i = 1; i < (ch + 1); i++)
+    {
+      if (ref & 1)
+	value |= 1 << (ch - i);
+      ref >>= 1;
+    }
+
+  return value;
+}
+
+u32 WIFI_calcCRC32 (u8 *data, int len)
+{
+  if (sizeof (u32) < 4)
+    exit (0);
+
+  u32 crc = 0xFFFFFFFF;
+
+  while (len--)
+    crc = (crc >> 8) ^ WIFI_CRC32Table[(crc & 0xFF) ^ *data++];
+
+  return (crc ^ 0xFFFFFFFF);
+}
+
+void WIFI_initCRC32Table ()
+{
+  if (sizeof (u32) < 4)
+    exit (0);
+
+  initialized = false;
+  if (initialized) return;
+  initialized = true;
+
+  u32 polynomial = 0x04C11DB7;
+
+  for (int i = 0; i < 0x100; i++)
+    {
+      WIFI_CRC32Table[i] = reflect (i, 8) << 24;
+      for (int j = 0; j < 8; j++)
+	WIFI_CRC32Table[i] = (WIFI_CRC32Table[i] << 1)
+			     ^ (WIFI_CRC32Table[i] & (1 << 31) ? polynomial
+							       : 0);
+      WIFI_CRC32Table[i] = reflect (WIFI_CRC32Table[i], 32);
+    }
+}
+
+int main ()
+{
+  if (sizeof (u32) < 4)
+    exit (0);
+
+  WIFI_initCRC32Table ();
+  WIFI_calcCRC32 ("dfsf", 4);
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-13.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-13.c
new file mode 100644
index 00000000000..79ca05276c7
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-13.c
@@ -0,0 +1,27 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+// crc.ii, CRC16
+#include <stdio.h>
+typedef unsigned short u16;
+
+void GenerateCRC32Table(u16 polynomial, u16 *table)
+{
+  for (u16 i = 0; i <= 255; i++) {
+      u16 crc = i;
+      for (u16 j = 0; j < 8; j++) { // latch's next bb is loop header
+	  crc = (crc >> 1) ^ ((crc & 1) ? 0x2342 : 0);
+	}
+      table[i] = crc;
+    }
+}
+
+int main ()
+{
+  u16 table [256];
+  GenerateCRC32Table (0x4, table);
+}
+
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-14.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-14.c
new file mode 100644
index 00000000000..7ed59cf2701
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-14.c
@@ -0,0 +1,35 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+// File - base64, slightly modified
+// We don't support the case when leading bit of the polynomial is kept.
+
+#include <stdint.h>
+#include <stdlib.h>
+
+uint32_t b64crc (const unsigned char* data, size_t ns)
+{
+  if (sizeof (unsigned int) < 4)
+    exit (0);
+
+  const unsigned char *s = data;
+  uint32_t crc = 0xb704ceL;
+
+  while (ns-- > 0)
+    {
+      int i;
+      crc ^= (*s++) << 16;
+      for (i = 0; i < 8; i++)
+	{
+	  crc <<= 1;
+	  if (crc & 0x1000000)
+	    crc ^= 0x1864cfbL;
+	}
+    }
+  crc &= 0xffffff;
+  /* ... */
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{\[0, \]*0\\\}" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-15.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-15.c
new file mode 100644
index 00000000000..b343d0fa188
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-15.c
@@ -0,0 +1,30 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+// File - callerid
+
+unsigned short calc_crc(unsigned short crc, unsigned char data)
+{
+  unsigned int i, j, org, dst;
+  org = data;
+  dst = 0;
+
+  for (i = 0; i < 8; i++) {
+    org <<= 1;
+    dst >>= 1;
+    if (org & 0x100)
+      dst |= 0x80;
+  }
+  data = (unsigned char) dst;
+  crc ^= (unsigned int) data << (16 - 8);
+  for (j = 0; j < 8; j++) {
+    if (crc & 0x8000U)
+      crc = (crc << 1) ^ 0x1021U ;
+    else
+      crc <<= 1 ;
+  }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-16.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-16.c
new file mode 100644
index 00000000000..2e7768445f4
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-16.c
@@ -0,0 +1,17 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+// File - cc1541
+
+unsigned char
+crc8(unsigned char value)
+{
+  for (int i = 0; i < 8; ++i) {
+      value = (value & 0x80) ? ((value << 1) ^ 0x31) : (value << 1);
+    }
+
+  return value;
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-17.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-17.c
new file mode 100644
index 00000000000..a76d7767804
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-17.c
@@ -0,0 +1,52 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+// File - crc.i.
+// We don't support this case.
+
+#include <stdlib.h>
+#include <stdint.h>
+uint32_t crc24_calculate(uint32_t preset, const uint8_t *data, uint8_t len)
+{
+  uint32_t state = preset;
+  uint8_t i;
+
+  for (i = 0; i < len; i++) {
+      uint8_t n, cur = data[i];
+
+      for (n = 0; n < 8; n++) {
+	  int next_bit = (state ^ cur) & 1;
+
+	  cur >>= 1;
+	  state >>= 1;
+	  if (next_bit) {
+	      state |= 1 << 23;
+	      state ^= 0x5a6000;
+	    }
+	}
+    }
+
+  return state;
+}
+
+uint32_t crc24_reverse(uint32_t crc, const uint8_t *data, uint8_t len)
+{
+  uint32_t state = crc;
+  uint8_t i;
+
+  for (i = 0; i < len; i++) {
+      uint8_t n, cur = data[len - i - 1];
+
+      for (n = 0; n < 8; n++) {
+	  int top_bit = state >> 23;
+
+	  state = (state << 1) & 0xffffff;
+	  state |= top_bit ^ ((cur >> (7 - n)) & 1);
+	  if (top_bit)
+	    state ^= 0xb4c000;
+	}
+    }
+
+  return state;
+}
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-18.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-18.c
new file mode 100644
index 00000000000..b171fe1fe71
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-18.c
@@ -0,0 +1,31 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+// File - cryptobonrrxternd.i
+// We don't support this case.
+
+unsigned char PGP_input[2*100];
+unsigned long crc24(int len) {
+
+  if (sizeof (long) < 4)
+    __builtin_exit (0);
+
+  long crc;
+  crc = 0xB704CE;
+  int i,j;
+  j = 0;
+  while (len--) {
+      crc ^= (PGP_input[j]) << 16;
+      j++;
+      for (i = 0; i < 8; i++) {
+	  crc <<= 1;
+	  if (crc & 0x1000000){
+	      crc ^= 0x1864CFB;
+	    }
+	}
+    }
+  return crc & 0xFFFFFF;
+}
+
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{\[0, \]*0\\\}" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-19.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-19.c
new file mode 100644
index 00000000000..e03cff1de77
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-19.c
@@ -0,0 +1,59 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+// File - liboctasic_la-oct6100_chip_open
+// We don't support this case.
+
+typedef unsigned int UINT32;
+typedef UINT32 * PUINT32;
+typedef struct _OCT6100_INSTANCE_API_
+{
+
+   // tPOCT6100_SHARED_INFO pSharedInfo;
+
+    //PVOID pProcessContext;
+
+    //tOCT6100_USER_SERIAL_OBJECT ulApiSerObj;
+
+
+} tOCT6100_INSTANCE_API, *tPOCT6100_INSTANCE_API;
+
+UINT32 Oct6100ApiProductionCrc(
+    tPOCT6100_INSTANCE_API f_pApiInstance,
+    PUINT32 f_pulMessage,
+    UINT32 f_ulMessageLength,
+    PUINT32 f_pulCrcResult )
+{
+  UINT32 ulWidth = 32;
+  UINT32 ulKey, i, j;
+  UINT32 ulRemainder = 0;
+
+
+  ulRemainder = f_pulMessage[ f_ulMessageLength - 1 ];
+  for ( j = f_ulMessageLength - 1; j != 0xFFFFFFFF ; j-- )
+    {
+      for ( i = 0; i < ulWidth; i++ )
+	{
+	  if ( ( ( ulRemainder >> 0x1F ) & 0x1 ) == 0x1 )
+	    {
+	      ulKey = 0x8765DCBA;
+	    }
+	  else
+	    {
+	      ulKey = 0;
+	    }
+	  ulRemainder = ulRemainder ^ ulKey;
+
+	  ulRemainder = ulRemainder << 1;
+	  if ( j != 0 )
+	    {
+	      ulRemainder = ulRemainder | ( ( f_pulMessage[ j - 1 ] ) >> ( 0x1F - i ) );
+	    }
+	}
+    }
+
+  *f_pulCrcResult = ulRemainder;
+
+  return 0x00000000;
+}
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-2.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-2.c
new file mode 100644
index 00000000000..abc8fcf3f89
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-2.c
@@ -0,0 +1,26 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details -ftree-cselim" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+//File - Ac3 from Fedora, polynomial made const. Original crc-side-instr-21.c test
+#include <stddef.h>
+typedef unsigned short int16u;
+typedef unsigned char int8u;
+int CRC16_Init(int16u *Table)
+{
+    for (size_t Pos=0; Pos<256; Pos++)
+    {
+        Table[Pos]=(int16u)Pos<<8;
+
+        for(int8u bit=0; bit<8; bit++)
+        {
+            if (Table[Pos]&0x8000)
+                Table[Pos]=(Table[Pos]<<1)^0x2101;
+            else
+                Table[Pos]=Table[Pos]<<1;
+        }
+    }
+    return 0;
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-20.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-20.c
new file mode 100644
index 00000000000..2e669176455
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-20.c
@@ -0,0 +1,47 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+// File - scorelayout.i
+
+#include <stdlib.h>
+typedef unsigned char guchar;
+typedef unsigned int guint32;
+guint32
+bit_reverse (guint32 x)
+{
+  x = ((x & 0x55555555) << 1) | ((x >> 1) & 0x55555555);
+  x = ((x & 0x33333333) << 2) | ((x >> 2) & 0x33333333);
+  x = ((x & 0x0F0F0F0F) << 4) | ((x >> 4) & 0x0F0F0F0F);
+  x = (x << 24) | ((x & 0xFF00) << 8) | ((x >> 8) & 0xFF00) | (x >> 24);
+  return x;
+}
+
+guint32
+crc32 (guchar * message)
+{
+  if (sizeof (int) < 4)
+    exit (0);
+
+  int i, j;
+  guint32 byte, crc;
+  i = 0;
+  crc = 0xFFFFFFFF;
+  while (message[i] != 0)
+    {
+      byte = message[i];
+      byte = bit_reverse (byte);
+      for (j = 0; j <= 7; j++)
+	{
+	  if ((int) (crc ^ byte) < 0)
+	    crc = (crc << 1) ^ 0x04C11DB7;
+	  else
+	    crc = crc << 1;
+	  byte = byte << 1;
+	}
+      i = i + 1;
+    }
+  return bit_reverse (~crc);
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-21.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-21.c
new file mode 100644
index 00000000000..aa51adf8970
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-21.c
@@ -0,0 +1,58 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+// File - Unsafe_crc16.i
+
+long BGl_crczd2valuezd2zz__crc16z00(long BgL_valz00_4, long BgL_crcz00_5)
+{
+  {
+    {
+      long BgL_iz00_1796;
+      long BgL_valuez00_1797;
+      long BgL_crcz00_1798;
+
+      BgL_iz00_1796 = ((long) 0);
+      BgL_valuez00_1797 = (BgL_valz00_4 << (int) (((long) 8)));
+      BgL_crcz00_1798 = BgL_crcz00_5;
+      BgL_loopz00_1795:
+      if ((BgL_iz00_1796 == ((long) 8)))
+	{
+	  return BgL_crcz00_1798;
+	}
+      else
+	{
+	  long BgL_valuez00_1801;
+	  long BgL_crcz00_1802;
+
+	  BgL_valuez00_1801 = (BgL_valuez00_1797 << (int) (((long) 1)));
+	  BgL_crcz00_1802 = (BgL_crcz00_1798 << (int) (((long) 1)));
+	  {
+	    long BgL_crcz00_2209;
+	    long BgL_valuez00_2208;
+	    long BgL_iz00_2206;
+
+	    BgL_iz00_2206 = (BgL_iz00_1796 + ((long) 1));
+	    BgL_valuez00_2208 = BgL_valuez00_1801;
+	    if (
+		(((long) 0) ==
+		 (((long) 65536) & (BgL_crcz00_1802 ^ BgL_valuez00_1801))))
+	      {
+		BgL_crcz00_2209 = BgL_crcz00_1802;
+	      }
+	    else
+	      {
+		BgL_crcz00_2209 = (BgL_crcz00_1802 ^ ((long) 32773));
+	      }
+	    BgL_crcz00_1798 = BgL_crcz00_2209;
+	    BgL_valuez00_1797 = BgL_valuez00_2208;
+	    BgL_iz00_1796 = BgL_iz00_2206;
+	    goto BgL_loopz00_1795;
+	  }
+	}
+    }
+  }
+}
+
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0\\\}
+" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-22.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-22.c
new file mode 100644
index 00000000000..07d6afbf218
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-22.c
@@ -0,0 +1,27 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+// File - crrcsim-LoggerReader_byte.ii
+// We don't support this case.
+
+int crcReg;
+enum { crcPoly = 49 };
+void crcByteSchritt(unsigned char data)
+{
+  for (int i=0; i<8; i++)
+    {
+      crcReg <<= 1;
+
+
+      if ((data & 0x80) != 0)
+	crcReg |= 1;
+
+      data <<= 1;
+
+      if ((crcReg & 0x100) != 0)
+	crcReg = crcReg ^ crcPoly;
+    }
+
+  crcReg &= 0xFF;
+}
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-23.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-23.c
new file mode 100644
index 00000000000..c2f3fedc57a
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-23.c
@@ -0,0 +1,28 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+// File - ModbusComm.ii
+
+#include <stdint.h>
+uint16_t ModbusCrc(const uint8_t *data, unsigned int sz)
+{
+  static const uint16_t MODBUS_CRC_POLY = 0xA001;
+  uint16_t crc = 0xffff;
+
+  while (sz--)
+    {
+      crc ^= *data++;
+      for (unsigned int i = 0; i < 8; ++i)
+	{
+	  if (crc & 0x1)
+	    crc = (crc >> 1) ^ MODBUS_CRC_POLY;
+	  else
+	    crc >>= 1;
+	}
+    }
+
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-24.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-24.c
new file mode 100644
index 00000000000..96a7231ad24
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-24.c
@@ -0,0 +1,29 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details -ftree-cselim" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+// File - utils.ii
+/* We don't support the case when CRC variable's size is different from the
+   calculated CRC (I.e. in this case CRC 16 is calculated.)  */
+
+void crc_byte(const char data, unsigned int *crc16)
+{
+  int k;
+  unsigned c,d ;
+
+  c = data << 8 ;
+  d = c;
+
+  for (k = 0; k < 8; k++) {
+      *crc16 = (c & 0x8000) ^ *crc16;
+
+      if (*crc16 & 0x8000) {
+	  *crc16 = *crc16 << 1;
+	  *crc16 = *crc16 ^ 0x8005;
+	} else
+	*crc16 = *crc16 << 1;
+
+      d = d << 1;
+      c = d;
+    }
+}
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-3.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-3.c
new file mode 100644
index 00000000000..cb2454d4594
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-3.c
@@ -0,0 +1,22 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+#include <stdint.h>
+//File - as_format
+uint32_t crc32r(const uint8_t *data, uint32_t size)
+{
+
+    uint32_t crc = 0xffffffff;
+    for(uint32_t i=0; i != size; i++) {
+        crc = crc ^ data[i];
+        for(int j=0; j<8; j++)
+            if(crc & 1)
+                crc = (crc >> 1) ^ 0xedb88320;
+            else
+                crc = crc >> 1;
+    }
+    return ~crc;
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-4.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-4.c
new file mode 100644
index 00000000000..0e041a187cd
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-4.c
@@ -0,0 +1,22 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+// crc.ii
+typedef unsigned int u32;
+
+void GenerateCRC32Table (u32 polynomial, u32 *table)
+{
+  for (u32 i = 0; i <= 255; i++)
+    {
+      u32 crc = i;
+      for (u32 j = 0; j < 8; j++)
+	{
+	  crc = (crc >> 1) ^ ((crc & 1) ? 0x23428765 : 0);
+	}
+      table[i] = crc;
+    }
+}
+
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-5.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-5.c
new file mode 100644
index 00000000000..41a6418e8c3
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-5.c
@@ -0,0 +1,54 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+// crc32.i
+// We don't support this case.
+
+#include <stddef.h>
+typedef unsigned int u32;
+u32 gf2_multiply(u32 x, u32 y, u32 modulus)
+{
+    u32 product = x & 1 ? y : 0;
+    int i;
+
+    for (i = 0; i < 31; i++) {
+        product = (product >> 1) ^ (product & 1 ? modulus : 0);
+        x >>= 1;
+        product ^= x & 1 ? y : 0;
+    }
+
+    return product;
+}
+
+u32 crc32_generic_shift(u32 crc, size_t len,
+                        u32 polynomial)
+{
+    u32 power = 0x2101;
+    int i;
+
+    for (i = 0; i < 8 * (int)(len & 3); i++)
+        crc = (crc >> 1) ^ (crc & 1 ? 0x2101 : 0);
+
+    len >>= 2;
+    if (!len)
+        return crc;
+
+    for (;;) {
+
+        if (len & 1)
+            crc = gf2_multiply(crc, power, polynomial);
+
+        len >>= 1;
+        if (!len)
+            break;
+
+
+        power = gf2_multiply(power, power, polynomial);
+    }
+
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump "Loop iteration number isn't a constant." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 30" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-6.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-6.c
new file mode 100644
index 00000000000..7d2a93d6b75
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-6.c
@@ -0,0 +1,41 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+// libmng_chunk_io
+typedef unsigned int mng_uint32;
+typedef signed int mng_int32;
+typedef signed char mng_int8;
+typedef mng_int8 mng_bool;
+typedef struct mng_data_struct {
+    // ...
+    mng_uint32 aCRCtable [256];
+    mng_bool bCRCcomputed;
+    // ...
+} mng_data;
+
+typedef mng_data * mng_datap;
+void make_crc_table (mng_datap pData)
+{
+    mng_uint32 iC;
+    mng_int32 iN, iK;
+
+    for (iN = 0; iN < 256; iN++)
+    {
+        iC = (mng_uint32) iN;
+
+        for (iK = 0; iK < 8; iK++)
+        {
+            if (iC & 1)
+                iC = 0xedb88320U ^ (iC >> 1);
+            else
+                iC = iC >> 1;
+        }
+
+        pData->aCRCtable [iN] = iC;
+    }
+
+    pData->bCRCcomputed = 1;
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-7.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-7.c
new file mode 100644
index 00000000000..c4a21703973
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-7.c
@@ -0,0 +1,18 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+// File - lsf_decode, modified.
+// We don't support this case.
+
+#include <stddef.h>
+#include <stdint.h>
+
+uint16_t crc(uint8_t byte, uint16_t reg) {
+    for (size_t i = 0; i != 8; ++i) {
+        uint16_t msb = reg & 0x8000;
+        reg = ((reg << 1) & 0xFFFF) | ((byte >> (7 - i)) & 0x0001);
+        if (msb) reg ^= 0x5935;
+    }
+    return reg & 0xFFFF;
+}
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-8.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-8.c
new file mode 100644
index 00000000000..8757c6c83fa
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-8.c
@@ -0,0 +1,30 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stddef.h>
+// File - misc
+uint32_t _crc32(uint32_t crc, uint32_t data) {
+    int i;
+    crc = crc ^ data;
+
+    for (i = 0; i < 32; i++) {
+        if (crc & 0x80000000)
+            crc = (crc << 1) ^ 0x04C11DB7;
+        else
+            crc = (crc << 1);
+    }
+
+    return crc;
+}
+
+uint32_t stm_crc32(const uint8_t *data, size_t size) {
+    uint32_t crc = 0xffffffff;
+    const uint32_t *pend = (const uint32_t *) (data + size);
+    for (const uint32_t *p = (const uint32_t *) (data); p < pend; p++)
+        crc = _crc32(crc, *p);
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 2 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-9.c b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-9.c
new file mode 100644
index 00000000000..15bc07f0de3
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-from-fedora-packages-9.c
@@ -0,0 +1,49 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+// File - nvme_mi
+#include <stdlib.h>
+typedef unsigned int __u32;
+typedef unsigned char __u8;
+struct nvme_mi_msg_hdr {
+    __u8 type;
+    __u8 nmp;
+    __u8 meb;
+    __u8 rsvd0;
+} __attribute__((packed));
+
+struct nvme_mi_req {
+    struct nvme_mi_msg_hdr *hdr;
+    size_t hdr_len;
+    void *data;
+    size_t data_len;
+    __u32 mic;
+};
+__u32 nvme_mi_crc32_update (__u32 crc, void *data, size_t len)
+{
+  int i;
+
+  while (len--)
+    {
+      crc ^= *(unsigned char *) (data++);
+      for (i = 0; i < 8; i++)
+	crc = (crc >> 1) ^ ((crc & 1) ? 0x82F63B78 : 0);
+    }
+  return crc;
+}
+
+void nvme_mi_calc_req_mic (struct nvme_mi_req *req)
+{
+  if (sizeof (__u32) < 4)
+    exit (0);
+
+  __u32 crc = 0xffffffff;
+
+  crc = nvme_mi_crc32_update (crc, req->hdr, req->hdr_len);
+  crc = nvme_mi_crc32_update (crc, req->data, req->data_len);
+
+  req->mic = ~crc;
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-linux-1.c b/gcc/testsuite/gcc.dg/torture/crc-linux-1.c
new file mode 100644
index 00000000000..912fd6459d2
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-linux-1.c
@@ -0,0 +1,45 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+#include <stdlib.h>
+#define CRC32_POLY_BE 0x04c11db7
+#define RETVAL_OUT_OF_MEMORY		(-6)
+#define RETVAL_NOT_BZIP_DATA		(-2)
+#define RETVAL_OK			0
+
+struct bunzip_data {
+    unsigned int crc32Table[256];
+};
+
+
+int start_bunzip(struct bunzip_data **bdp, void *inbuf, long len,
+			     long (*fill)(void*, unsigned long))
+{
+  if (sizeof (unsigned int) <= 3)
+    exit (0);
+
+  struct bunzip_data *bd;
+  unsigned int i, j, c;
+
+  /* Figure out how much data to allocate */
+  i = sizeof(struct bunzip_data);
+
+  /* Allocate bunzip_data.  Most fields initialize to zero. */
+  bd = *bdp = malloc(i);
+
+  /* ... */
+
+  /* Init the CRC32 table (big endian) */
+  for (i = 0; i < 256; i++) {
+      c = i << 24;
+      for (j = 8; j; j--)
+	c = c&0x80000000 ? (c << 1)^(CRC32_POLY_BE) : (c << 1);
+      bd->crc32Table[i] = c;
+    }
+
+  /* . . . */
+  return RETVAL_OK;
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-linux-2.c b/gcc/testsuite/gcc.dg/torture/crc-linux-2.c
new file mode 100644
index 00000000000..366ea0f814f
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-linux-2.c
@@ -0,0 +1,65 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stddef.h>
+typedef unsigned char  u8;
+typedef unsigned short u16;
+typedef unsigned char __u8;
+typedef unsigned short __u16;
+struct i2c_msg {
+    __u16 addr;
+    __u16 flags;
+#define I2C_M_RD                0x0001  /* guaranteed to be 0x0001! */
+    /* ... */
+    __u16 len;
+    __u8 *buf;
+};
+
+#define POLY    (0x1070U << 3)
+static u8 crc8(u16 data)
+{
+  int i;
+
+  for (i = 0; i < 8; i++) {
+      if (data & 0x8000)
+	data = data ^ POLY;
+      data = data << 1;
+    }
+  return (u8)(data >> 8);
+}
+
+/**
+* i2c_smbus_pec - Incremental CRC8 over the given input data array
+* @crc: previous return crc8 value
+* @p: pointer to data buffer.
+* @count: number of bytes in data buffer.
+*
+* Incremental CRC8 over count bytes in the array pointed to by p
+*/
+u8 i2c_smbus_pec(u8 crc, u8 *p, size_t count)
+{
+  int i;
+
+  for (i = 0; i < count; i++)
+    crc = crc8((crc ^ p[i]) << 8);
+  return crc;
+}
+static inline u8 i2c_8bit_addr_from_msg(const struct i2c_msg *msg)
+{
+  return (msg->addr << 1) | (msg->flags & I2C_M_RD ? 1 : 0);
+}
+
+
+/* Assume a 7-bit address, which is reasonable for SMBus */
+u8 i2c_smbus_msg_pec(u8 pec, struct i2c_msg *msg)
+{
+  /* The address will be sent first */
+  u8 addr = i2c_8bit_addr_from_msg(msg);
+  pec = i2c_smbus_pec(pec, &addr, 1);
+
+  /* The data buffer follows */
+  return i2c_smbus_pec(pec, msg->buf, msg->len);
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-linux-3.c b/gcc/testsuite/gcc.dg/torture/crc-linux-3.c
new file mode 100644
index 00000000000..301f6d22b65
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-linux-3.c
@@ -0,0 +1,49 @@ 
+/* We don't find this case because in "crc32_generic_shift" function
+   loop's iteration number isn't a constant (i < 8 * (int)(len & 3)).  */
+
+#include <stddef.h>
+typedef unsigned int u32;
+#define __attribute_const__	__attribute__((__const__))
+static u32 __attribute_const__ gf2_multiply (u32 x, u32 y, u32 modulus)
+{
+  u32 product = x & 1 ? y : 0;
+  int i;
+
+  for (i = 0; i < 31; i++)
+    {
+      product = (product >> 1) ^ (product & 1 ? modulus : 0);
+      x >>= 1;
+      product ^= x & 1 ? y : 0;
+    }
+  return product;
+}
+
+u32 __attribute_const__ crc32_generic_shift(u32 crc, size_t len,
+                                                  u32 polynomial)
+{
+       u32 power = polynomial; /* CRC of x^32 */
+       int i;
+
+       /* Shift up to 32 bits in the simple linear way */
+       for (i = 0; i < 8 * (int)(len & 3); i++)
+               crc = (crc >> 1) ^ (crc & 1 ? polynomial : 0);
+
+       len >>= 2;
+       if (!len)
+               return crc;
+
+       for (;;) {
+               /* "power" is x^(2^i), modulo the polynomial */
+               if (len & 1)
+                       crc = gf2_multiply(crc, power, polynomial);
+
+               len >>= 1;
+               if (!len)
+                       break;
+
+               /* Square power, advancing to x^(2^(i+1)) */
+               power = gf2_multiply(power, power, polynomial);
+       }
+
+       return crc;
+}
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-linux-4.c b/gcc/testsuite/gcc.dg/torture/crc-linux-4.c
new file mode 100644
index 00000000000..7f5b34a40f1
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-linux-4.c
@@ -0,0 +1,30 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details -w" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+/* We don't detect, it's optimized to branch-less CRC.  */
+#define CRC32_POLY_LE 0xedb88320
+typedef unsigned int u32;
+u32 calc_crc(unsigned char *buf, int len)
+{
+  u32 reg;
+  u32 tmp;
+  int j, k;
+
+  reg = 0xffffffff;
+
+  for (j = 0; j < len; j++) {
+      reg ^= buf[j];
+
+      for (k = 0; k < 8; k++) {
+	  tmp = reg & 0x01;
+
+	  reg >>= 1;
+
+	  if (tmp)
+	    reg ^= CRC32_POLY_LE;
+	}
+    }
+
+  return ~reg;
+}
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-linux-5.c b/gcc/testsuite/gcc.dg/torture/crc-linux-5.c
new file mode 100644
index 00000000000..419659c78e1
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-linux-5.c
@@ -0,0 +1,81 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stddef.h>
+#include <stdint.h>
+/* We don't find, as we can't replace the first loop,
+   and in the second loop polynomials leading 1 bit is kept too
+   (second function's iteration count is 4).  */
+typedef unsigned char  u8;
+typedef unsigned short u16;
+u8 drm_dp_msg_data_crc4(const uint8_t *data, u8 number_of_bytes)
+{
+  u8 bitmask = 0x80;
+  u8 bitshift = 7;
+  u8 array_index = 0;
+  int number_of_bits = number_of_bytes * 8;
+  u16 remainder = 0;
+
+  while (number_of_bits != 0) {
+      number_of_bits--;
+      remainder <<= 1;
+      remainder |= (data[array_index] & bitmask) >> bitshift;
+      bitmask >>= 1;
+      bitshift--;
+      if (bitmask == 0) {
+	  bitmask = 0x80;
+	  bitshift = 7;
+	  array_index++;
+	}
+      if ((remainder & 0x100) == 0x100)
+	remainder ^= 0xd5;
+    }
+
+  number_of_bits = 8;
+  while (number_of_bits != 0) {
+      number_of_bits--;
+      remainder <<= 1;
+      if ((remainder & 0x100) != 0)
+	remainder ^= 0xd5;
+    }
+
+  return remainder & 0xff;
+}
+
+/* sideband msg handling */
+u8 drm_dp_msg_header_crc4(const uint8_t *data, size_t num_nibbles)
+{
+  u8 bitmask = 0x80;
+  u8 bitshift = 7;
+  u8 array_index = 0;
+  int number_of_bits = num_nibbles * 4;
+  u8 remainder = 0;
+
+  while (number_of_bits != 0) {
+      number_of_bits--;
+      remainder <<= 1;
+      remainder |= (data[array_index] & bitmask) >> bitshift;
+      bitmask >>= 1;
+      bitshift--;
+      if (bitmask == 0) {
+	  bitmask = 0x80;
+	  bitshift = 7;
+	  array_index++;
+	}
+      if ((remainder & 0x10) == 0x10)
+	remainder ^= 0x13;
+    }
+
+  number_of_bits = 4;
+  while (number_of_bits != 0) {
+      number_of_bits--;
+      remainder <<= 1;
+      if ((remainder & 0x10) != 0)
+	remainder ^= 0x13;
+    }
+
+  return remainder;
+}
+
+/* { dg-final { scan-tree-dump "drm_dp_msg_data_crc4 function maybe contains CRC calculation." "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-1.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-1.c
new file mode 100644
index 00000000000..9ebc28d5e7e
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-1.c
@@ -0,0 +1,28 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+//loop iteration number is 5
+ee_u16 not_crcu8 (ee_u8 data, ee_u16 crc) {
+    ee_u8 i = 0, x16 = 0, carry = 0;
+    for (i = 0; i < 5; i++) {
+        x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+        data >>= 1;
+        if (x16 == 1) {
+            crc ^= 0x4002;
+            carry = 1;
+        } else
+            carry = 0;
+        crc >>= 1;
+        if (carry)
+            crc |= 0x8000;
+        else
+            crc &= 0x7fff;
+    }
+    return crc;
+}
+/* { dg-final { scan-tree-dump-times "crcu8 function maybe contains CRC calculation" 0 "crc"} } */
+
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-10.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-10.c
new file mode 100644
index 00000000000..540916423e6
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-10.c
@@ -0,0 +1,23 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+//Spoiled crc value
+uint16_t not_crc(uint16_t crc, uint8_t a) {
+    int i;
+    crc ^= a;
+    for (i = 0; i < 8; ++i) {
+        if (crc & 1) {
+            crc = 0;
+            crc = (crc << 1) ^ 0xA001;
+        }
+        else
+            crc = crc >> 1;
+    }
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "not_crc function maybe contains CRC calculation" 0 "crc"} } */
+
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-11.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-11.c
new file mode 100644
index 00000000000..4b9592ea919
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-11.c
@@ -0,0 +1,26 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+ee_u16 not_crc(ee_u8 data, ee_u16 crc) {
+    ee_u8 i = 0, carry = 0;
+    for (i = 0; i < 8; i++) {
+        data >>= 1;
+        if (data == 1) {
+            crc ^= 0x4002;
+            carry = 1;
+        } else
+            carry = 0;
+        crc >>= 1;
+        if (carry)
+            crc |= 0x8000;
+        else
+            crc &= 0x7fff;
+    }
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "not_crc function maybe contains CRC calculation" 0 "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-12.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-12.c
new file mode 100644
index 00000000000..4b58513e2a3
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-12.c
@@ -0,0 +1,18 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint8_t not_crc(uint8_t crc, uint8_t data) {
+    uint8_t i;
+    crc = crc ^ data;
+    for (i = 0; i < 8; i++) {
+        if (data & 0x01)
+            crc = (crc >> 1) ^ 0x8C;
+        else
+            crc >>= 1;
+    }
+    return crc;
+}
+/* { dg-final { scan-tree-dump-times "not_crc function maybe contains CRC calculation" 0 "crc"} } */
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-13.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-13.c
new file mode 100644
index 00000000000..e2ae1274ff8
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-13.c
@@ -0,0 +1,21 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint8_t not_crc(uint8_t crc, uint8_t data) {
+  uint8_t i;
+  crc = crc ^ data;
+  for (i = 0; i < 8; i++) {
+      if (crc & 0x01)
+	crc = (crc >> 1) ^ 0x8C;
+      else
+	crc >>= 1;
+      if (i > 1)
+	crc = 8;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-14.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-14.c
new file mode 100644
index 00000000000..4ed8c154ac7
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-14.c
@@ -0,0 +1,21 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint8_t not_crc(uint8_t crc, uint8_t data) {
+  crc = crc ^ data;
+
+  for (uint8_t i = 0, n = 0; i < 8; i++, n++) {
+      if (data > i)
+	crc = 8;
+      if (crc & 0x01)
+	crc = (crc >> 1) ^ 0x8C;
+      else
+	crc >>= 1;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-15.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-15.c
new file mode 100644
index 00000000000..ae95517d0a0
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-15.c
@@ -0,0 +1,23 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-O3" "-flto"} } */
+
+/* With -O3 the cycles is split into 2,
+   and one of them calculates CRC (when data != 0).
+   Thus, when compiling with -O3 there is CRC. */
+
+#include <stdint.h>
+
+uint8_t not_crc(uint8_t crc, uint8_t data) {
+  crc = crc ^ data;
+
+  for (uint8_t i = 0, n = 0; i < 8; i++, n++) {
+      if ((crc & 0x01) && data)
+	crc = (crc >> 1) ^ 0x8C;
+      else
+	crc >>= 1;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-16.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-16.c
new file mode 100644
index 00000000000..e644956a586
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-16.c
@@ -0,0 +1,19 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint8_t not_crc(uint8_t crc, uint8_t data) {
+  uint8_t i;
+  crc = crc ^ data;
+  for (i = 0; i < 8; i++) {
+      if (!i && (crc & 0x01))
+	crc = (crc >> 1) ^ 0x8C;
+      else
+	crc >>= 1;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-17.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-17.c
new file mode 100644
index 00000000000..36c3ae05e78
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-17.c
@@ -0,0 +1,19 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint8_t not_crc(uint8_t crc, uint8_t data) {
+  uint8_t i;
+  crc = crc ^ data;
+  for (i = 0; i < 8; i++) {
+      if (i && (crc & 0x01))
+	crc = (crc >> 1) ^ 0x8C;
+      else
+	crc >>= 1;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-18.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-18.c
new file mode 100644
index 00000000000..6acf91cf806
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-18.c
@@ -0,0 +1,19 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint8_t not_crc(uint8_t crc, uint8_t data) {
+  uint8_t i;
+  crc = crc ^ data;
+  for (i = 0; i < 8; i++) {
+      if ((crc & 0x01) && i==0)
+	crc = (crc >> 1) ^ 0x8C;
+      else
+	crc >>= 1;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-19.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-19.c
new file mode 100644
index 00000000000..513135871ec
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-19.c
@@ -0,0 +1,19 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint8_t not_crc(uint8_t crc, uint8_t data) {
+  uint8_t i;
+  crc = crc ^ data;
+  for (i = 0; i < 8; i++) {
+      if ((crc & 0x01) || i==0)
+	crc = (crc >> 1) ^ 0x8C;
+      else
+	crc >>= 1;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-2.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-2.c
new file mode 100644
index 00000000000..6bef6a6ef74
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-2.c
@@ -0,0 +1,28 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+typedef uint8_t crc;
+#define TOPBIT (1 << 7)
+
+//shift not by one
+crc
+notCrc(uint8_t const message[], int nBytes) {
+    crc remainder = 0;
+    for (int byte = 0; byte < nBytes; ++byte) {
+        remainder ^= message[byte] ;
+        for (uint8_t bit = 8; bit > 0; --bit) {
+            if (remainder & TOPBIT) {
+                remainder = (remainder << 3) ^ 1234;
+            } else {
+                remainder = (remainder << 9);
+            }
+        }
+    }
+    return (remainder);
+}
+
+/* { dg-final { scan-tree-dump-times "notCrc function maybe contains CRC calculation" 0 "crc"} } */
+
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-20.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-20.c
new file mode 100644
index 00000000000..4a02a4da7a6
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-20.c
@@ -0,0 +1,19 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint8_t not_crc(uint8_t crc, uint8_t data) {
+  uint8_t i;
+  crc = crc ^ data;
+  for (i = 0; i < 8; i++) {
+      if (i == 0 || (crc & 0x01))
+	crc = (crc >> 1) ^ 0x8C;
+      else
+	crc >>= 1;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-21.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-21.c
new file mode 100644
index 00000000000..e45dd1bf2f4
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-21.c
@@ -0,0 +1,26 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint16_t not_crcu8 (uint8_t data, uint16_t crc) {
+  uint8_t i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      x16 = (uint8_t)((data & 128) ^ ((uint8_t) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-22.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-22.c
new file mode 100644
index 00000000000..4f8460607c1
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-22.c
@@ -0,0 +1,26 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint16_t not_crcu8 (uint8_t data, uint16_t crc) {
+  uint8_t i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      x16 = (uint8_t) ((data & 2) ^ ((uint8_t) crc & 2));
+      data >>= 1;
+      if (x16 == 2) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-23.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-23.c
new file mode 100644
index 00000000000..96544e6a3ec
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-23.c
@@ -0,0 +1,26 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint16_t not_crcu8 (uint8_t data, uint16_t crc) {
+  uint8_t i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      x16 = (uint8_t) ((data & 1) ^ ((uint8_t) crc & 1)  ^ (i & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-24.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-24.c
new file mode 100644
index 00000000000..4932c68a85c
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-24.c
@@ -0,0 +1,26 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint16_t not_crcu8 (uint8_t data, uint16_t crc) {
+  uint8_t i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      x16 = (uint8_t) (((uint8_t) crc & 1)  ^ (i & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-25.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-25.c
new file mode 100644
index 00000000000..19ba9af53c2
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-25.c
@@ -0,0 +1,26 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint16_t not_crcu8 (uint8_t *data, uint16_t crc) {
+  uint8_t x16 = 0, carry = 0;
+  for (uint8_t i = 0, j=4; i < 8; i++, j+=2) {
+      x16 = (uint8_t) (((uint8_t) crc & 1)  ^ (j & 1));
+      *data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-26.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-26.c
new file mode 100644
index 00000000000..3718ab3b31a
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-26.c
@@ -0,0 +1,26 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint16_t not_crcu8 (uint8_t data, uint16_t crc) {
+  uint8_t x16 = 0, carry = 0;
+  for (uint8_t i = 0, j=3; i < 8; i++, j+=2) {
+      x16 = (uint8_t) (((uint8_t) crc & 1)  ^ (j & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-3.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-3.c
new file mode 100644
index 00000000000..8b7523e16b9
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-3.c
@@ -0,0 +1,22 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+//no shift in case of xor
+uint16_t not_crc16_update(uint16_t crc, uint8_t a) {
+	
+    int i;
+    crc ^= a;
+    for (i = 0; i < 8; ++i) {
+        if (crc & 1)
+            crc = crc ^ 0xA001;
+        else
+            crc = (crc >> 1);
+    }
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "not_crc16_update function maybe contains CRC calculation" 0 "crc"} } */
+
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-4.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-4.c
new file mode 100644
index 00000000000..cc6e2b08650
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-4.c
@@ -0,0 +1,19 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+//shift and xor only if lsb is 1
+uint16_t not_crc(uint16_t crc, uint8_t a) {
+    int i;
+    crc ^= a;
+    for (i = 0; i < 8; ++i) {
+        if (crc & 1)
+            crc = (crc >> 1) ^ 0xA001;
+    }
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "not_crc function maybe contains CRC calculation" 0 "crc"} } */
+
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-5.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-5.c
new file mode 100644
index 00000000000..234a2a1cda1
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-5.c
@@ -0,0 +1,27 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdio.h>
+
+typedef unsigned char uint8_t;
+
+//no xor
+uint8_t not_crc(uint8_t *data, size_t len) {
+    uint8_t crc = 0xff;
+    size_t i, j;
+    for (i = 0; i < len; i++) {
+        crc ^= data[i];
+        for (j = 0; j < 8; j++) {
+            if ((crc & 0x80) != 0)
+                crc = (uint8_t) ((crc << 1) | 0x31);
+            else
+                crc <<= 1;
+        }
+    }
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "not_crc function maybe contains CRC calculation" 0 "crc"} } */
+
+
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-6.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-6.c
new file mode 100644
index 00000000000..aa692014dd7
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-6.c
@@ -0,0 +1,24 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+#define POLY (0x1070U << 3)
+#define u8 uint8_t
+#define u16 uint16_t
+
+//xor in case 0
+u8 not_crc(u16 data) {
+    int i;
+    for (i = 0; i < 8; i++) {
+        if (data & 0x0000)
+            data = data ^ POLY;
+        data = data << 1;
+    }
+    return (u8)(data >> 8);
+}
+
+/* { dg-final { scan-tree-dump-times "not_crc function maybe contains CRC calculation" 0 "crc"} } */
+
+
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-7.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-7.c
new file mode 100644
index 00000000000..622431a94b8
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-7.c
@@ -0,0 +1,20 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+//in one case is called shift left, in another shift right
+uint16_t not_crc(uint16_t crc, uint8_t a) {
+    int i;
+    crc ^= a;
+    for (i = 0; i < 8; ++i) {
+        if (crc & 1)
+            crc = (crc << 1) ^ 0xA001;
+        else
+            crc = crc >> 1;
+    }
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "not_crc function maybe contains CRC calculation" 0 "crc"} } */
+
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-8.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-8.c
new file mode 100644
index 00000000000..90c2ea61bb6
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-8.c
@@ -0,0 +1,21 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+//xor is done in case lsb is 0
+int16_t not_crc(int16_t crc, int8_t a) {
+    int i;
+    crc ^= a;
+    for (i = 0; i < 8; ++i) {
+        if (crc << 15 == 0)
+            crc = (crc >> 1) ^ 0xA001;
+        else
+            crc = crc >> 1;
+    }
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "not_crc function maybe contains CRC calculation" 0 "crc"} } */
+
diff --git a/gcc/testsuite/gcc.dg/torture/crc-not-crc-9.c b/gcc/testsuite/gcc.dg/torture/crc-not-crc-9.c
new file mode 100644
index 00000000000..38c54120b01
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-not-crc-9.c
@@ -0,0 +1,17 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+//no conditional xor
+uint16_t not_crc(uint16_t crc, uint8_t a) {
+    int i;
+    crc ^= a;
+    for (i = 0; i < 8; ++i) {
+            crc = (crc << 1) ^ 0xA001;
+    }
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "not_crc function maybe contains CRC calculation" 0 "crc"} } */
+
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-1.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-1.c
new file mode 100644
index 00000000000..003321bb7ab
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-1.c
@@ -0,0 +1,27 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint16_t crc16_update (uint16_t crc, uint8_t a)
+{
+  int i;
+  for (i = 0; i < 8; ++i)
+    {
+      int b;
+      if ((crc & 1) ^ (a & 1))
+	crc = (crc >> 1) ^ 0xa001;
+      else
+	crc = (crc >> 1);
+      a >>= 1;
+      b = crc; // Unused instruction, this is safe to remove.
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump "crc16_update function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1\\\}" "crc" } } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-10.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-10.c
new file mode 100644
index 00000000000..f0ea2dc467e
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-10.c
@@ -0,0 +1,31 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+  ee_u16 i = 0, x16 = 0, carry = 0;
+  int a = 1;
+  for (i = 0; i < 8; i++) {
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      a = a * (crc + 5);
+      if (carry)
+	{
+	  crc |= 0x8000;
+	}
+      else
+	crc &= 0x7fff;
+    }
+  return a;
+}
+
+/* { dg-final { scan-tree-dump "Output CRC and determined input CRC differ." "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-11.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-11.c
new file mode 100644
index 00000000000..74cc61310da
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-11.c
@@ -0,0 +1,31 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+  ee_u16 i = 0, x16 = 0, carry = 0;
+  int a = 1;
+  for (i = 0; i < 8; i++) {
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      a = a * (crc + 5);
+      if (carry)
+	{
+	  crc |= 0x8000;
+	}
+      else
+	crc &= 0x7fff;
+    }
+  return a + crc;
+}
+
+/* { dg-final { scan-tree-dump "There is more than one output phi." "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-12.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-12.c
new file mode 100644
index 00000000000..b8b00e62a6a
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-12.c
@@ -0,0 +1,33 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+int a;
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+  ee_u16 i = 0, x16 = 0, carry = 0;
+  int c;
+  for (i = 0; i < 8; i++) {
+      c += i*2; // In compiled code, it is moved outside of the loop.
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      a = c;
+      if (carry)
+	{
+	  crc |= 0x8000;
+	}
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-13.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-13.c
new file mode 100644
index 00000000000..e59a111ec92
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-13.c
@@ -0,0 +1,31 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+int a;
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+    ee_u16 i = 0, x16 = 0, carry = 0;
+    int c;
+    for (i = 0; i < 8; i++) {
+        c += crc * 2;
+        x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+        data >>= 1;
+        if (x16 == 1) {
+            crc ^= 0x4002;
+            carry = 1;
+        } else
+            carry = 0;
+        crc >>= 1;
+        a = c;
+        if (carry) {
+            crc |= 0x8000;
+        } else
+            crc &= 0x7fff;
+    }
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump "There is more than one output phi." "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-14.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-14.c
new file mode 100644
index 00000000000..57f611123d8
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-14.c
@@ -0,0 +1,35 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdio.h>
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+int a;
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+    ee_u16 i = 0, x16 = 0, carry = 0;
+    int c;
+    for (i = 0; i < 8; i++) {
+        c += i*2;
+        printf ("%d", c);
+        x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+        data >>= 1;
+        if (x16 == 1) {
+            crc ^= 0x4002;
+            carry = 1;
+        } else
+            carry = 0;
+        crc >>= 1;
+        a = c;
+        if (carry)
+        {
+            crc |= 0x8000;
+        }
+        else
+            crc &= 0x7fff;
+    }
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-15.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-15.c
new file mode 100644
index 00000000000..e6cd72ec9c6
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-15.c
@@ -0,0 +1,37 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+int foo (int c)
+{
+    return c*c;
+}
+
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+    ee_u16 i = 0, x16 = 0, carry = 0;
+    int c;
+    for (i = 0; i < 8; i++) {
+        c += i*2;
+        c = foo (c); // All calculations related to c are removed.
+        x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+        data >>= 1;
+        if (x16 == 1) {
+            crc ^= 0x4002;
+            carry = 1;
+        } else
+            carry = 0;
+        crc >>= 1;
+        if (carry)
+        {
+            crc |= 0x8000;
+        }
+        else
+            crc &= 0x7fff;
+    }
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-16.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-16.c
new file mode 100644
index 00000000000..f357f5ef176
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-16.c
@@ -0,0 +1,38 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+__attribute__ ((noinline,noipa))
+int foo (int c)
+{
+    return c*c;
+}
+
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+    ee_u16 i = 0, x16 = 0, carry = 0;
+    int c;
+    for (i = 0; i < 8; i++) {
+        c += i*2;
+        c = foo (c); //Warning, encountered unsupported statement, while executing gimple statements!
+        x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+        data >>= 1;
+        if (x16 == 1) {
+            crc ^= 0x4002;
+            carry = 1;
+        } else
+            carry = 0;
+        crc >>= 1;
+        if (carry)
+        {
+            crc |= 0x8000;
+        }
+        else
+            crc &= 0x7fff;
+    }
+    return crc;
+}
+
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-17.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-17.c
new file mode 100644
index 00000000000..66f2877722d
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-17.c
@@ -0,0 +1,37 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+int foo (int c)
+{
+    return c*c;
+}
+
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+    ee_u16 i = 0, x16 = 0, carry = 0;
+    int c;
+    for (i = 0; i < 8; i++) {
+        c += i*2;
+        c = foo (c);
+        x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+        data >>= 1;
+        if (x16 == 1) {
+            crc ^= 0x4002;
+            carry = 1;
+        } else
+            carry = 0;
+        crc >>= 1;
+        if (carry)
+        {
+            crc |= 0x8000;
+        }
+        else
+            crc &= 0x7fff;
+    }
+    return crc + c;
+}
+
+/* { dg-final { scan-tree-dump "There is more than one output phi." "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-2.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-2.c
new file mode 100644
index 00000000000..326124e869e
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-2.c
@@ -0,0 +1,27 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdio.h>
+
+uint16_t crc16_update(uint16_t crc, uint8_t a) {
+  int i;
+  int b;
+  for (i = 0; i < 8; ++i) {
+      if ((crc & 1) ^ (a & 1))
+	crc = (crc >> 1) ^ 0xa001;
+      else
+	crc = (crc >> 1);
+      a >>= 1;
+      b = crc; // Unused instruction, this is safe to remove.
+    }
+    printf ("%d", b);
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump "crc16_update function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1\\\}" "crc" } } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-3.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-3.c
new file mode 100644
index 00000000000..9073c397408
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-3.c
@@ -0,0 +1,26 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint16_t crc16_update(uint16_t crc, uint8_t a) {
+  int i;
+  int b;
+  for (i = 0; i < 8; ++i) {
+      if ((crc & 1) ^ (a & 1))
+	crc = (crc >> 1) ^ 0xa001;
+      else
+	crc = (crc >> 1);
+      a >>= 1;
+      b = crc;
+    }
+  int c = b; // This is removed from the compiled code.
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump "crc16_update function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1\\\}" "crc" } } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-4.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-4.c
new file mode 100644
index 00000000000..38ec17001ca
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-4.c
@@ -0,0 +1,26 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint16_t crc16_update(uint16_t crc, uint8_t a) {
+  int i;
+  uint16_t b;
+  for (i = 0; i < 8; ++i) {
+      if ((crc & 1) ^ (a & 1))
+	crc = (crc >> 1) ^ 0xa001;
+      else
+	crc = (crc >> 1);
+      a >>= 1;
+      b = crc;
+    }
+  uint16_t c = b++; // This is removed from the compiled code.
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump "crc16_update function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1\\\}" "crc" } } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-5.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-5.c
new file mode 100644
index 00000000000..1bffdd16e34
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-5.c
@@ -0,0 +1,26 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+
+uint16_t crc16_update(uint16_t crc, uint8_t a) {
+  int i;
+  uint16_t b;
+  for (i = 0; i < 8; ++i) {
+      if ((crc & 1) ^ (a & 1))
+	crc = (crc >> 1) ^ 0xa001;
+      else
+	crc = (crc >> 1);
+      a >>= 1;
+      b = crc; // In compiled version, b is outside of the loop.
+    }
+  uint16_t c = ++b;
+  return c;
+}
+
+/* { dg-final { scan-tree-dump "crc16_update function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1\\\}" "crc" } } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-6.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-6.c
new file mode 100644
index 00000000000..7fe395f4934
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-6.c
@@ -0,0 +1,42 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdint.h>
+#include <stdio.h>
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+int a;
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+  ee_u8 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      a++; // this is moved outside of the loop
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+int main()
+{
+  printf ("%04X\n", crcu8 (0, 0xaa));
+  printf ("%d", a);
+}
+
+
+/* { dg-final { scan-tree-dump "crcu8 function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump "calculates CRC!" "crc"} } */
+/* { dg-final { scan-tree-dump "Polynomial's value is \\\{\[0, \]*1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1\\\}" "crc" } } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-7.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-7.c
new file mode 100644
index 00000000000..1ef3aea9aac
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-7.c
@@ -0,0 +1,40 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdio.h>
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+int a[10] = {};
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+  ee_u8 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      a[i] = crc;
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+int main()
+{
+  printf ("%04X\n", crcu8 (0, 0xaa));
+  printf ("%d", a[0]);
+}
+
+
+/* { dg-final { scan-tree-dump "crcu8 function maybe contains CRC calculation." "crc"} } */
+/* { dg-final { scan-tree-dump "Loop iteration number is 7" "crc"} } */
+/* { dg-final { scan-tree-dump "Bit reversed" "crc"} } */
+/* { dg-final { scan-tree-dump-times "calculates CRC!" 0 "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-8.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-8.c
new file mode 100644
index 00000000000..9777aadec78
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-8.c
@@ -0,0 +1,36 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+#include <stdio.h>
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+int a;
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+  ee_u8 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      a += crc; // Defined variable is used outside the loop.
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	crc |= 0x8000;
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+int main()
+{
+  printf ("%04X\n", crcu8 (0, 0xaa));
+  printf ("%d", a);
+}
+
+/* { dg-final { scan-tree-dump "There is more than one output phi." "crc"} } */
\ No newline at end of file
diff --git a/gcc/testsuite/gcc.dg/torture/crc-side-instr-9.c b/gcc/testsuite/gcc.dg/torture/crc-side-instr-9.c
new file mode 100644
index 00000000000..0d235789dbf
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/crc-side-instr-9.c
@@ -0,0 +1,31 @@ 
+/* { dg-do compile } */
+/* { dg-options "-fdump-tree-crc-details" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" "-O1" "-Os" "-flto"} } */
+
+typedef unsigned short ee_u16;
+typedef unsigned char ee_u8;
+
+int a;
+ee_u16 crcu8 (ee_u8 data, ee_u16 crc) {
+  ee_u8 i = 0, x16 = 0, carry = 0;
+  for (i = 0; i < 8; i++) {
+      x16 = (ee_u8) ((data & 1) ^ ((ee_u8) crc & 1));
+      data >>= 1;
+      if (x16 == 1) {
+	  crc ^= 0x4002;
+	  carry = 1;
+	} else
+	carry = 0;
+      crc >>= 1;
+      if (carry)
+	{
+	  a = crc;
+	  crc |= 0x8000;
+	}
+      else
+	crc &= 0x7fff;
+    }
+  return crc;
+}
+
+/* { dg-final { scan-tree-dump "There is more than one output phi." "crc"} } */
\ No newline at end of file
-- 
2.25.1