Linux Kernel  3.7.1
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
ecrc.c
Go to the documentation of this file.
1 /*
2  * Enables/disables PCIe ECRC checking.
3  *
4  * (C) Copyright 2009 Hewlett-Packard Development Company, L.P.
5  * Andrew Patterson <[email protected]>
6  *
7  * This program is free software; you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation; version 2 of the License.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14  * General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
19  * 02111-1307, USA.
20  *
21  */
22 
23 #include <linux/kernel.h>
24 #include <linux/module.h>
25 #include <linux/moduleparam.h>
26 #include <linux/pci.h>
27 #include <linux/pci_regs.h>
28 #include <linux/errno.h>
29 #include "../../pci.h"
30 
31 #define ECRC_POLICY_DEFAULT 0 /* ECRC set by BIOS */
32 #define ECRC_POLICY_OFF 1 /* ECRC off for performance */
33 #define ECRC_POLICY_ON 2 /* ECRC on for data integrity */
34 
35 static int ecrc_policy = ECRC_POLICY_DEFAULT;
36 
37 static const char *ecrc_policy_str[] = {
38  [ECRC_POLICY_DEFAULT] = "bios",
39  [ECRC_POLICY_OFF] = "off",
40  [ECRC_POLICY_ON] = "on"
41 };
42 
49 static int enable_ecrc_checking(struct pci_dev *dev)
50 {
51  int pos;
52  u32 reg32;
53 
54  if (!pci_is_pcie(dev))
55  return -ENODEV;
56 
58  if (!pos)
59  return -ENODEV;
60 
61  pci_read_config_dword(dev, pos + PCI_ERR_CAP, &reg32);
62  if (reg32 & PCI_ERR_CAP_ECRC_GENC)
63  reg32 |= PCI_ERR_CAP_ECRC_GENE;
64  if (reg32 & PCI_ERR_CAP_ECRC_CHKC)
65  reg32 |= PCI_ERR_CAP_ECRC_CHKE;
66  pci_write_config_dword(dev, pos + PCI_ERR_CAP, reg32);
67 
68  return 0;
69 }
70 
77 static int disable_ecrc_checking(struct pci_dev *dev)
78 {
79  int pos;
80  u32 reg32;
81 
82  if (!pci_is_pcie(dev))
83  return -ENODEV;
84 
86  if (!pos)
87  return -ENODEV;
88 
89  pci_read_config_dword(dev, pos + PCI_ERR_CAP, &reg32);
91  pci_write_config_dword(dev, pos + PCI_ERR_CAP, reg32);
92 
93  return 0;
94 }
95 
101 {
102  switch (ecrc_policy) {
103  case ECRC_POLICY_DEFAULT:
104  return;
105  case ECRC_POLICY_OFF:
106  disable_ecrc_checking(dev);
107  break;
108  case ECRC_POLICY_ON:
109  enable_ecrc_checking(dev);
110  break;
111  default:
112  return;
113  }
114 }
115 
120 {
121  int i;
122 
123  for (i = 0; i < ARRAY_SIZE(ecrc_policy_str); i++)
124  if (!strncmp(str, ecrc_policy_str[i],
125  strlen(ecrc_policy_str[i])))
126  break;
127  if (i >= ARRAY_SIZE(ecrc_policy_str))
128  return;
129 
130  ecrc_policy = i;
131 }