1 /***********************license start***************
2 * Copyright (c) 2003-2010 Cavium Networks (support@cavium.com). All rights
3 * reserved.
4 *
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions are
8 * met:
9 *
10 * * Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 *
13 * * Redistributions in binary form must reproduce the above
14 * copyright notice, this list of conditions and the following
15 * disclaimer in the documentation and/or other materials provided
16 * with the distribution.
17
18 * * Neither the name of Cavium Networks nor the names of
19 * its contributors may be used to endorse or promote products
20 * derived from this software without specific prior written
21 * permission.
22
23 * This Software, including technical data, may be subject to U.S. export control
24 * laws, including the U.S. Export Administration Act and its associated
25 * regulations, and may be subject to export or import regulations in other
26 * countries.
27
28 * TO THE MAXIMUM EXTENT PERMITTED BY LAW, THE SOFTWARE IS PROVIDED "AS IS"
29 * AND WITH ALL FAULTS AND CAVIUM NETWORKS MAKES NO PROMISES, REPRESENTATIONS OR
30 * WARRANTIES, EITHER EXPRESS, IMPLIED, STATUTORY, OR OTHERWISE, WITH RESPECT TO
31 * THE SOFTWARE, INCLUDING ITS CONDITION, ITS CONFORMITY TO ANY REPRESENTATION OR
32 * DESCRIPTION, OR THE EXISTENCE OF ANY LATENT OR PATENT DEFECTS, AND CAVIUM
33 * SPECIFICALLY DISCLAIMS ALL IMPLIED (IF ANY) WARRANTIES OF TITLE,
34 * MERCHANTABILITY, NONINFRINGEMENT, FITNESS FOR A PARTICULAR PURPOSE, LACK OF
35 * VIRUSES, ACCURACY OR COMPLETENESS, QUIET ENJOYMENT, QUIET POSSESSION OR
36 * CORRESPONDENCE TO DESCRIPTION. THE ENTIRE RISK ARISING OUT OF USE OR
37 * PERFORMANCE OF THE SOFTWARE LIES WITH YOU.
38 ***********************license end**************************************/
39
40
41 /**
42 * @file
43 *
44 * Interface to the Octeon extended error status.
45 *
46 * <hr>$Revision: 44252 $<hr>
47 */
48 #ifndef __CVMX_ERROR_H__
49 #define __CVMX_ERROR_H__
50
51 #ifdef __cplusplus
52 extern "C" {
53 #endif
54
55 /**
56 * There are generally many error status bits associated with a
57 * single logical group. The enumeration below is used to
58 * communicate high level groups to the error infastructure so
59 * error status bits can be enable or disabled in large groups.
60 */
61 typedef enum
62 {
63 CVMX_ERROR_GROUP_INTERNAL, /* All internal blocks that can always be enabled */
64 CVMX_ERROR_GROUP_ETHERNET, /* All errors related to network traffic that should be enabled when a port is up. Indexed by IPD number */
65 CVMX_ERROR_GROUP_MGMT_PORT, /* All errors related to the management ethernet ports that should be enabled when a port is up. Indexed by port number (0-1) */
66 CVMX_ERROR_GROUP_PCI, /* All errors related to PCI/PCIe when the bus is up. Index by port number (0-1) */
67 CVMX_ERROR_GROUP_SRIO, /* All errors related to SRIO when the bus is up. Index by port number (0-1) */
68 CVMX_ERROR_GROUP_USB, /* All errors related to USB when the port is enabled. Index by port number (0-1) */
69 CVMX_ERROR_GROUP_LMC, /* All errors related to LMC when the controller is enabled. Index by controller number (0-1) */
70 } cvmx_error_group_t;
71
72 /**
73 * When registering for interest in an error status register, the
74 * type of the register needs to be known by cvmx-error. Most
75 * registers are either IO64 or IO32, but some blocks contain
76 * registers that can't be directly accessed. A good example of
77 * would be PCIe extended error state stored in config space.
78 */
79 typedef enum
80 {
81 __CVMX_ERROR_REGISTER_NONE, /* Used internally */
82 CVMX_ERROR_REGISTER_IO64, /* Status and enable registers are Octeon 64bit CSRs */
83 CVMX_ERROR_REGISTER_IO32, /* Status and enable registers are Octeon 32bit CSRs */
84 CVMX_ERROR_REGISTER_PCICONFIG, /* Status and enable registers are in PCI config space */
85 CVMX_ERROR_REGISTER_SRIOMAINT, /* Status and enable registers are in SRIO maintenance space */
86 } cvmx_error_register_t;
87
88 /**
89 * Flags representing special handling for some error registers.
90 * These flags are passed to cvmx_error_initialize() to control
91 * the handling of bits where the same flags were passed to the
92 * added cvmx_error_info_t.
93 */
94 typedef enum
95 {
96 CVMX_ERROR_FLAGS_ECC_SINGLE_BIT = 1<<0, /* This is a ECC single bit error. Normally these can be ignored */
97 CVMX_ERROR_FLAGS_CORRECTABLE = 1<<1, /* Some blocks have errors that can be silently corrected. This flags reports these */
98 CVMX_ERROR_FLAGS_DISABLED = 1<<2, /* Flag used to signal a register should not be enable as part of the groups */
99 } cvmx_error_flags_t;
100
101 struct cvmx_error_info;
102 /**
103 * Error handling functions must have the following prototype.
104 */
105 typedef int (*cvmx_error_func_t)(const struct cvmx_error_info *info);
106
107 /**
108 * This structure is passed to all error handling functions.
109 */
110 typedef struct cvmx_error_info
111 {
112 cvmx_error_register_t reg_type; /* Type of registers used for the error */
113 uint64_t status_addr; /* The address of the status register */
114 uint64_t status_mask; /* Mask to apply to status register to detect asserted error */
115 uint64_t enable_addr; /* The address of the enable register */
116 uint64_t enable_mask; /* Mask to apply to enable register to allow error detection */
117 cvmx_error_flags_t flags; /* Flags indicating special handling of this error */
118 cvmx_error_group_t group; /* Group to associate this error register with */
119 int group_index; /* Group index to associate this error register with */
120 cvmx_error_func_t func; /* Function to call when the error is detected */
121 uint64_t user_info; /* User supplied information for the error handler */
122 struct
123 {
124 cvmx_error_register_t reg_type; /* Type of parent's register */
125 uint64_t status_addr; /* The address of the parent's register */
126 uint64_t status_mask; /* Mask to apply to parent's register */
127 } parent;
128 } cvmx_error_info_t;
129
130 /**
131 * Initalize the error status system. This should be called once
132 * before any other functions are called. This function adds default
133 * handlers for most all error events but does not enable them. Later
134 * calls to cvmx_error_enable() are needed.
135 *
136 * @param flags Optional flags.
137 *
138 * @return Zero on success, negative on failure.
139 */
140 int cvmx_error_initialize(cvmx_error_flags_t flags);
141
142 /**
143 * Poll the error status registers and call the appropriate error
144 * handlers. This should be called in the RSL interrupt handler
145 * for your application or operating system.
146 *
147 * @return Number of error handlers called. Zero means this call
148 * found no errors and was spurious.
149 */
150 int cvmx_error_poll(void);
151
152 /**
153 * Register to be called when an error status bit is set. Most users
154 * will not need to call this function as cvmx_error_initialize()
155 * registers default handlers for most error conditions. This function
156 * is normally used to add more handlers without changing the existing
157 * handlers.
158 *
159 * @param new_info Information about the handler for a error register. The
160 * structure passed is copied and can be destroyed after the
161 * call. All members of the structure must be populated, even the
162 * parent information.
163 *
164 * @return Zero on success, negative on failure.
165 */
166 int cvmx_error_add(const cvmx_error_info_t *new_info);
167
168 /**
169 * Remove all handlers for a status register and mask. Normally
170 * this function should not be called. Instead a new handler should be
171 * installed to replace the existing handler. In the even that all
172 * reporting of a error bit should be removed, then use this
173 * function.
174 *
175 * @param reg_type Type of the status register to remove
176 * @param status_addr
177 * Status register to remove.
178 * @param status_mask
179 * All handlers for this status register with this mask will be
180 * removed.
181 * @param old_info If not NULL, this is filled with information about the handler
182 * that was removed.
183 *
184 * @return Zero on success, negative on failure (not found).
185 */
186 int cvmx_error_remove(cvmx_error_register_t reg_type,
187 uint64_t status_addr, uint64_t status_mask,
188 cvmx_error_info_t *old_info);
189
190 /**
191 * Change the function and user_info for an existing error status
192 * register. This function should be used to replace the default
193 * handler with an application specific version as needed.
194 *
195 * @param reg_type Type of the status register to change
196 * @param status_addr
197 * Status register to change.
198 * @param status_mask
199 * All handlers for this status register with this mask will be
200 * changed.
201 * @param new_func New function to use to handle the error status
202 * @param new_user_info
203 * New user info parameter for the function
204 * @param old_func If not NULL, the old function is returned. Useful for restoring
205 * the old handler.
206 * @param old_user_info
207 * If not NULL, the old user info parameter.
208 *
209 * @return Zero on success, negative on failure
210 */
211 int cvmx_error_change_handler(cvmx_error_register_t reg_type,
212 uint64_t status_addr, uint64_t status_mask,
213 cvmx_error_func_t new_func, uint64_t new_user_info,
214 cvmx_error_func_t *old_func, uint64_t *old_user_info);
215
216 /**
217 * Enable all error registers for a logical group. This should be
218 * called whenever a logical group is brought online.
219 *
220 * @param group Logical group to enable
221 * @param group_index
222 * Index for the group as defined in the cvmx_error_group_t
223 * comments.
224 *
225 * @return Zero on success, negative on failure.
226 */
227 #ifndef CVMX_BUILD_FOR_UBOOT
228 int cvmx_error_enable_group(cvmx_error_group_t group, int group_index);
229 #else
230 /* Rather than conditionalize the calls throughout the executive to not enable
231 interrupts in Uboot, simply make the enable function do nothing */
cvmx_error_enable_group(cvmx_error_group_t group,int group_index)232 static inline int cvmx_error_enable_group(cvmx_error_group_t group, int group_index)
233 {
234 return 0;
235 }
236 #endif
237
238 /**
239 * Disable all error registers for a logical group. This should be
240 * called whenever a logical group is brought offline. Many blocks
241 * will report spurious errors when offline unless this function
242 * is called.
243 *
244 * @param group Logical group to disable
245 * @param group_index
246 * Index for the group as defined in the cvmx_error_group_t
247 * comments.
248 *
249 * @return Zero on success, negative on failure.
250 */
251 #ifndef CVMX_BUILD_FOR_UBOOT
252 int cvmx_error_disable_group(cvmx_error_group_t group, int group_index);
253 #else
254 /* Rather than conditionalize the calls throughout the executive to not disable
255 interrupts in Uboot, simply make the enable function do nothing */
cvmx_error_disable_group(cvmx_error_group_t group,int group_index)256 static inline int cvmx_error_disable_group(cvmx_error_group_t group, int group_index)
257 {
258 return 0;
259 }
260 #endif
261
262 /**
263 * Enable all handlers for a specific status register mask.
264 *
265 * @param reg_type Type of the status register
266 * @param status_addr
267 * Status register address
268 * @param status_mask
269 * All handlers for this status register with this mask will be
270 * enabled.
271 *
272 * @return Zero on success, negative on failure.
273 */
274 int cvmx_error_enable(cvmx_error_register_t reg_type,
275 uint64_t status_addr, uint64_t status_mask);
276
277 /**
278 * Disable all handlers for a specific status register and mask.
279 *
280 * @param reg_type Type of the status register
281 * @param status_addr
282 * Status register address
283 * @param status_mask
284 * All handlers for this status register with this mask will be
285 * disabled.
286 *
287 * @return Zero on success, negative on failure.
288 */
289 int cvmx_error_disable(cvmx_error_register_t reg_type,
290 uint64_t status_addr, uint64_t status_mask);
291
292 /**
293 * @INTERNAL
294 * Function for processing non leaf error status registers. This function
295 * calls all handlers for this passed register and all children linked
296 * to it.
297 *
298 * @param info Error register to check
299 *
300 * @return Number of error status bits found or zero if no bits were set.
301 */
302 int __cvmx_error_decode(const cvmx_error_info_t *info);
303
304 /**
305 * @INTERNAL
306 * This error bit handler simply prints a message and clears the status bit
307 *
308 * @param info Error register to check
309 *
310 * @return
311 */
312 int __cvmx_error_display(const cvmx_error_info_t *info);
313
314 #ifdef __cplusplus
315 }
316 #endif
317
318 #endif
319