Commit | Line | Data |
---|---|---|
800f879a AT |
1 | /* |
2 | * Copyright 2010-2017 Intel Corporation. | |
3 | * | |
4 | * This program is free software; you can redistribute it and/or modify | |
5 | * it under the terms of the GNU General Public License, version 2, | |
6 | * as published by the Free Software Foundation. | |
7 | * | |
8 | * This program is distributed in the hope that it will be useful, | |
9 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
10 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
11 | * General Public License for more details. | |
12 | * | |
13 | * Disclaimer: The codes contained in these modules may be specific to | |
14 | * the Intel Software Development Platform codenamed Knights Ferry, | |
15 | * and the Intel product codenamed Knights Corner, and are not backward | |
16 | * compatible with other Intel products. Additionally, Intel will NOT | |
17 | * support the codes or instruction set in future products. | |
18 | * | |
19 | * Intel offers no warranty of any kind regarding the code. This code is | |
20 | * licensed on an "AS IS" basis and Intel is not obligated to provide | |
21 | * any support, assistance, installation, training, or other services | |
22 | * of any kind. Intel is also not obligated to provide any updates, | |
23 | * enhancements or extensions. Intel specifically disclaims any warranty | |
24 | * of merchantability, non-infringement, fitness for any particular | |
25 | * purpose, and any other warranty. | |
26 | * | |
27 | * Further, Intel disclaims all liability of any kind, including but | |
28 | * not limited to liability for infringement of any proprietary rights, | |
29 | * relating to the use of the code, even if Intel is notified of the | |
30 | * possibility of such liability. Except as expressly stated in an Intel | |
31 | * license agreement provided with this code and agreed upon with Intel, | |
32 | * no license, express or implied, by estoppel or otherwise, to any | |
33 | * intellectual property rights is granted herein. | |
34 | */ | |
35 | ||
36 | #if !defined(__MIC_COMMON_H) | |
37 | #define __MIC_COMMON_H | |
38 | ||
39 | #ifdef __cplusplus | |
40 | extern "C" { | |
41 | #endif | |
42 | ||
43 | #include <linux/errno.h> | |
44 | #include <linux/hardirq.h> | |
45 | #include <linux/types.h> | |
46 | #include <linux/capability.h> | |
47 | #include <linux/slab.h> | |
48 | #include <linux/string.h> | |
49 | #include <linux/gfp.h> | |
50 | #include <linux/vmalloc.h> | |
51 | #include <asm/io.h> | |
52 | #include <linux/kernel.h> | |
53 | #include <linux/mm_types.h> | |
54 | #include <linux/jiffies.h> | |
55 | #include <linux/timer.h> | |
56 | #include <linux/irqflags.h> | |
57 | #include <linux/time.h> | |
58 | #include <linux/spinlock.h> | |
59 | #include <linux/mutex.h> | |
60 | #include <linux/semaphore.h> | |
61 | #include <linux/kthread.h> | |
62 | #include <linux/sched.h> | |
63 | #include <linux/delay.h> | |
64 | #include <linux/wait.h> | |
65 | #include <asm/bug.h> | |
66 | #include <linux/pci.h> | |
67 | #include <linux/device.h> | |
68 | #include <linux/fs.h> | |
69 | #include <linux/list.h> | |
70 | #include <linux/workqueue.h> | |
71 | #include <linux/interrupt.h> | |
72 | #include <asm/atomic.h> | |
73 | #include <linux/netdevice.h> | |
74 | #include <linux/debugfs.h> | |
75 | #include <mic/bootparams.h> | |
76 | #include <mic/micsboxdefine.h> | |
77 | #include <mic/micdboxdefine.h> | |
78 | #include <mic/ringbuffer.h> | |
79 | #include <mic/micscif.h> | |
80 | #ifdef USE_VCONSOLE | |
81 | #include <mic/micvcons.h> | |
82 | #endif | |
83 | #include <mic/micpsmi.h> | |
84 | #include <mic/io_interface.h> | |
85 | #include <mic/mic_pm.h> | |
86 | #include <mic/mic_dma_api.h> | |
87 | #include <mic/micveth_common.h> | |
88 | #include <mic/micscif_nm.h> | |
89 | ||
90 | #define GET_MAX(a, b) ( ((a) > (b)) ? (a) : (b) ) | |
91 | #define GET_MIN(a, b) ( ((a) < (b)) ? (a) : (b) ) | |
92 | ||
93 | // System Interrupt Cause Read Register 0 | |
94 | #define SBOX_SICR0_DBR(x) ((x) & 0xf) | |
95 | #define SBOX_SICR0_DMA(x) (((x) >> 8) & 0xff) | |
96 | ||
97 | // System Interrupt Cause Enable Register 0 | |
98 | #define SBOX_SICE0_DBR(x) ((x) & 0xf) | |
99 | #define SBOX_SICE0_DBR_BITS(x) ((x) & 0xf) | |
100 | #define SBOX_SICE0_DMA(x) (((x) >> 8) & 0xff) | |
101 | #define SBOX_SICE0_DMA_BITS(x) (((x) & 0xff) << 8) | |
102 | ||
103 | // System Interrupt Cause Read Register 1 | |
104 | #define SBOX_SICR1_SBOXERR(x) ((x) & 0x1) | |
105 | #define SBOX_SICR1_SPIDONE(x) (((x) >> 4) & 0x1) | |
106 | ||
107 | // System Interrupt Cause Set Register 1 | |
108 | #define SBOX_SICC1_SBOXERR(x) ((x) & 0x1) | |
109 | #define SBOX_SICC1_SPIDONE(x) (((x) >> 4) & 0x1) | |
110 | ||
111 | // Offsets in the MMIO Range for register segments | |
112 | #define HOST_DBOX_BASE_ADDRESS 0x00000000 | |
113 | #define HOST_SBOX_BASE_ADDRESS 0x00010000 | |
114 | #define HOST_GTT_BASE_ADDRESS 0x00040000 | |
115 | ||
116 | #define SCRATCH0_MEM_TEST_DISABLE(x) ((x) & 0x1) | |
117 | #define SCRATCH0_MEM_USAGE(x) (((x) >> 1) & 0x3) | |
118 | #define SCR0_MEM_ALL 0x0 | |
119 | #define SCR0_MEM_HALF 0x1 | |
120 | #define SCR0_MEM_THIRD 0x2 | |
121 | #define SCR0_MEM_FOURTH 0x3 | |
122 | #define SCRATCH0_MEM_SIZE_KB(x) ((x) >> 0x3) | |
123 | ||
124 | #define SCRATCH2_DOWNLOAD_STATUS(x) ((x) & 0x1) | |
125 | ||
126 | #define SCRATCH2_CLEAR_DOWNLOAD_STATUS(x) ((x) & ~0x1) | |
127 | #define SCRATCH2_APIC_ID(x) (((x) >> 1) & 0x1ff) | |
128 | #define SCRATCH2_DOWNLOAD_ADDR(x) ((x) & 0xfffff000) | |
129 | ||
130 | #define SCRATCH13_SUB_STEP(x) ((x) & 0xf) | |
131 | #define SCRATCH13_STEP_ID(x) (((x) >> 4) & 0xf) | |
132 | #define SCRATCH13_PLATFORM_ID(x) (((x) >> 18) & 0x3) | |
133 | ||
134 | ||
135 | #define MEMVOLT_MEMVOLT(x) (((x) >>SHIFT_MEMVOLT) & MASK_MEMVOLT) | |
136 | #define MEMFREQ_MEMFREQ(x) (((x) >>SHIFT_MEMORYFREQ) & MASK_MEMORYFREQ) | |
137 | #define FAILSAFEOFFSET_FAILSAFE(x) (((x) >>SHIFT_FAIL_SAFE) & MASK_FAIL_SAFE) | |
138 | ||
139 | #define SCRATCH4_ACTIVE_CORES(x) (((x) >>SHIFT_ACTIVE_CORES) & MASK_ACTIVE_CORES) | |
140 | #define SCRATCH0_MEMSIZE(x) (((x) >>SHIFT_MEMSIZE) & MASK_MEMSIZE) | |
141 | #define SCRATCH7_FLASHVERSION(x) (((x) >>SHIFT_FLASHVERSION) & MASK_FLASHVERSION) | |
142 | #define SCRATCH7_FUSECONFIGREV(x) (((x) >>SHIFT_FUSE_CONFIG_REV) & MASK_FUSE_CONFIG_REV) | |
143 | #define SCRATCH13_MODEL(x) (((x) >>SHIFT_MODEL) & MASK_MODEL) | |
144 | #define SCRATCH13_FAMILY_DATA(x) (((x) >>SHIFT_FAMILY_DATA) & MASK_FAMILY_DATA) | |
145 | #define SCRATCH13_PROCESSOR(x) (((x) >>SHIFT_PROCESSOR) & MASK_PROCESSOR) | |
146 | #define SCRATCH13_EXTENDED_MODEL(x) (((x) >>SHIFT_EXTENDED_MODEL) & MASK_EXTENDED_MODEL) | |
147 | #define SCRATCH13_EXTENDED_FAMILY(x) (((x) >>SHIFT_EXTENDED_FAMILY) & MASK_EXTENDED_FAMILY) | |
148 | ||
149 | ||
150 | #define DBOX_READ(mmio, offset) \ | |
151 | readl((uint32_t*)((uint8_t*)(mmio) + (HOST_DBOX_BASE_ADDRESS + (offset)))) | |
152 | #define DBOX_WRITE(value, mmio, offset) \ | |
153 | writel((value), (uint32_t*)((uint8_t*)(mmio) + (HOST_DBOX_BASE_ADDRESS + (offset)))) | |
154 | ||
155 | #define SBOX_READ(mmio, offset) \ | |
156 | readl((uint32_t*)((uint8_t*)(mmio) + (HOST_SBOX_BASE_ADDRESS + (offset)))) | |
157 | #define SBOX_WRITE(value, mmio, offset) \ | |
158 | writel((value), (uint32_t*)((uint8_t*)(mmio) + (HOST_SBOX_BASE_ADDRESS + (offset)))) | |
159 | ||
160 | #define SET_BUS_DEV_FUNC(bus, device, function, reg_offset) \ | |
161 | (( bus << 16 ) | ( device << 11 ) | ( function << 8 ) | reg_offset) | |
162 | ||
163 | #define GTT_READ(mmio, offset) \ | |
164 | readl((uint32_t*)((uint8_t*)(mmio) + (HOST_GTT_BASE_ADDRESS + (offset)))) | |
165 | #define GTT_WRITE(value, mmio, offset) \ | |
166 | writel((value), (uint32_t*)((uint8_t*)(mmio) + (HOST_GTT_BASE_ADDRESS + (offset)))) | |
167 | ||
168 | ||
169 | #define ENABLE_MIC_INTERRUPTS(mmio) { \ | |
170 | uint32_t sboxSice0reg = SBOX_READ((mmio), SBOX_SICE0); \ | |
171 | sboxSice0reg |= SBOX_SICE0_DBR_BITS(0xf) | SBOX_SICE0_DMA_BITS(0xff); \ | |
172 | SBOX_WRITE(sboxSice0reg, (mmio), SBOX_SICE0); } | |
173 | ||
174 | #ifndef ARRAY_SIZE | |
175 | #define ARRAY_SIZE(x) (sizeof(x)/sizeof((x)[0])) | |
176 | #endif | |
177 | ||
178 | #define DLDR_APT_BAR 0 | |
179 | #define DLDR_MMIO_BAR 4 | |
180 | ||
181 | #define PCI_VENDOR_INTEL 0x8086 | |
182 | ||
183 | #define PCI_DEVICE_ABR_2249 0x2249 | |
184 | #define PCI_DEVICE_ABR_224a 0x224a | |
185 | ||
186 | #define PCI_DEVICE_KNC_2250 0x2250 | |
187 | #define PCI_DEVICE_KNC_2251 0x2251 | |
188 | #define PCI_DEVICE_KNC_2252 0x2252 | |
189 | #define PCI_DEVICE_KNC_2253 0x2253 | |
190 | #define PCI_DEVICE_KNC_2254 0x2254 | |
191 | #define PCI_DEVICE_KNC_2255 0x2255 | |
192 | #define PCI_DEVICE_KNC_2256 0x2256 | |
193 | #define PCI_DEVICE_KNC_2257 0x2257 | |
194 | #define PCI_DEVICE_KNC_2258 0x2258 | |
195 | #define PCI_DEVICE_KNC_2259 0x2259 | |
196 | #define PCI_DEVICE_KNC_225a 0x225a | |
197 | ||
198 | #define PCI_DEVICE_KNC_225b 0x225b | |
199 | #define PCI_DEVICE_KNC_225c 0x225c | |
200 | #define PCI_DEVICE_KNC_225d 0x225d | |
201 | #define PCI_DEVICE_KNC_225e 0x225e | |
202 | ||
203 | #define MIC_CMDLINE_BUFSIZE 1024 | |
204 | #define RESET_FAIL_TIME 300 | |
205 | ||
206 | /* Masks for sysfs entries */ | |
207 | #ifdef CONFIG_ML1OM | |
208 | #define MASK_COREVOLT 0xff | |
209 | #define MASK_COREFREQ 0xfff | |
210 | #endif | |
211 | #define MASK_MEMVOLT 0xff | |
212 | #define MASK_MEMORYFREQ 0xff | |
213 | #define MASK_MEMSIZE 0x1fffffff | |
214 | #define MASK_FLASHVERSION 0xffff | |
215 | #define MASK_SUBSTEPPING_DATA 0xf | |
216 | #define MASK_STEPPING_DATA 0xf | |
217 | #define MASK_MODEL 0xf | |
218 | #define MASK_FAMILY_DATA 0xf | |
219 | #define MASK_PROCESSOR 0x3 | |
220 | #define MASK_PLATFORM 0x3 | |
221 | #define MASK_EXTENDED_MODEL 0xf | |
222 | #define MASK_EXTENDED_FAMILY 0xff | |
223 | #define MASK_FUSE_CONFIG_REV 0x3ff | |
224 | #define MASK_ACTIVE_CORES 0x3f | |
225 | #define MASK_FAIL_SAFE 0xffffffff | |
226 | #define MASK_FLASH_UPDATE 0xffffffff | |
227 | /* Shifts for sysfs entries */ | |
228 | #ifdef CONFIG_ML1OM | |
229 | #define SHIFT_COREVOLT 0 | |
230 | #define SHIFT_COREFREQ 0 | |
231 | #endif | |
232 | #define SHIFT_MEMVOLT 0 | |
233 | #define SHIFT_MEMORYFREQ 0 | |
234 | #define SHIFT_MEMSIZE 3 | |
235 | #define SHIFT_FLASHVERSION 16 | |
236 | #define SHIFT_SUBSTEPPING_DATA 0 | |
237 | #define SHIFT_STEPPING_DATA 4 | |
238 | #define SHIFT_MODEL 8 | |
239 | #define SHIFT_FAMILY_DATA 12 | |
240 | #define SHIFT_PROCESSOR 16 | |
241 | #define SHIFT_PLATFORM 18 | |
242 | #define SHIFT_EXTENDED_MODEL 20 | |
243 | #define SHIFT_EXTENDED_FAMILY 24 | |
244 | #define SHIFT_FUSE_CONFIG_REV 0 | |
245 | #define SHIFT_ACTIVE_CORES 10 | |
246 | #define SHIFT_FAIL_SAFE 0 | |
247 | #define SHIFT_FLASH_UPDATE 0 | |
248 | ||
249 | #define SKU_NAME_LEN 20 | |
250 | ||
251 | /* Should be updated to reflect the latest interface version in sysfs and wmi property */ | |
252 | #define LINUX_INTERFACE_VERSION "1.0" | |
253 | #define WINDOWS_INTERFACE_VERSION "1.0" | |
254 | ||
255 | typedef enum mic_modes | |
256 | { | |
257 | MODE_NONE, | |
258 | MODE_LINUX, | |
259 | MODE_ELF, | |
260 | MODE_FLASH | |
261 | } MIC_MODES; | |
262 | ||
263 | typedef enum mic_status | |
264 | { | |
265 | MIC_READY, | |
266 | MIC_BOOT, | |
267 | MIC_NORESPONSE, | |
268 | MIC_BOOTFAIL, | |
269 | MIC_ONLINE, | |
270 | MIC_SHUTDOWN, | |
271 | MIC_LOST, | |
272 | MIC_RESET, | |
273 | MIC_RESETFAIL, | |
274 | MIC_INVALID | |
275 | } MIC_STATUS; | |
276 | ||
277 | typedef enum _product_platform_t | |
278 | { | |
279 | PLATFORM_SILICON = 0, | |
280 | PLATFORM_EMULATOR = 2, | |
281 | }product_platform_t; | |
282 | ||
283 | ||
284 | typedef enum _platform_resource_type | |
285 | { | |
286 | PCI_APERTURE, | |
287 | MMIO, | |
288 | MAX_RESOURCE_TYPE | |
289 | }platform_resource_type; | |
290 | ||
291 | typedef struct _platform_resource_t | |
292 | { | |
293 | uint8_t* va; // mapped by driver | |
294 | uint64_t pa; // from PCI config space | |
295 | uint64_t len;// from PCI config space | |
296 | }platform_resource_t; | |
297 | ||
298 | ||
299 | typedef struct micscifhost_info { | |
300 | dma_addr_t si_pa; | |
301 | struct delayed_work si_bs_check; | |
302 | uint32_t si_bs_wait_count; | |
303 | } scifhost_info_t; | |
304 | ||
305 | #define MIC_NUM_DB 4 | |
306 | typedef struct mic_irq { | |
307 | spinlock_t mi_lock; | |
308 | struct list_head mi_dblist[MIC_NUM_DB]; // The 4 doorbell interrupts. | |
309 | atomic_t mi_received; | |
310 | } mic_irq_t; | |
311 | ||
312 | typedef struct sysfs_info { | |
313 | char *cmdline; | |
314 | char *kernel_cmdline; | |
315 | } sysfs_info_t; | |
316 | ||
317 | typedef struct pm_recv_msg { | |
318 | struct list_head msg; | |
319 | pm_msg_header msg_header; | |
320 | void * msg_body; | |
321 | } pm_recv_msg_t; | |
322 | ||
323 | typedef struct pm_wq { | |
324 | struct workqueue_struct *wq; | |
325 | struct work_struct work; | |
326 | char wq_name[20]; | |
327 | } pm_wq_t; | |
328 | ||
329 | /* | |
330 | * Driver wide power management context | |
331 | * common power management context for all the devices | |
332 | */ | |
333 | typedef struct micscif_pm { | |
334 | scif_epd_t epd; | |
335 | atomic_t connected_clients; | |
336 | pm_wq_t accept; | |
337 | struct mutex pm_accept_mutex; | |
338 | struct mutex pm_idle_mutex; | |
339 | struct dentry *pmdbgparent_dir; | |
340 | uint32_t enable_pm_logging; | |
341 | atomic_t wakeup_in_progress; | |
342 | uint8_t *nodemask; | |
343 | uint32_t nodemask_len; | |
344 | } micscif_pm_t; | |
345 | ||
346 | /* per device power management context */ | |
347 | typedef struct micpm_ctx | |
348 | { | |
349 | scif_epd_t pm_epd; | |
350 | PM_IDLE_STATE idle_state; | |
351 | struct mutex msg_mutex; | |
352 | struct list_head msg_list; | |
353 | uint32_t pc6_timeout; | |
354 | struct work_struct pm_close; | |
355 | MIC_STATUS mic_suspend_state; | |
356 | bool pc3_enabled; | |
357 | bool pc6_enabled; | |
358 | pm_msg_pm_options pm_options; | |
359 | atomic_t pm_ref_cnt; | |
360 | platform_resource_t nodemask; | |
361 | pm_wq_t recv; | |
362 | pm_wq_t handle_msg; | |
363 | pm_wq_t resume; | |
364 | struct workqueue_struct *pc6_entry_wq; | |
365 | struct delayed_work pc6_entry_work; | |
366 | char pc6_wq_name[20]; | |
367 | struct dentry *pmdbg_dir; | |
368 | PM_CONNECTION_STATE con_state; | |
369 | wait_queue_head_t disc_wq; | |
370 | } micpm_ctx_t; | |
371 | ||
372 | typedef struct _mic_ctx_t { | |
373 | platform_resource_t mmio; | |
374 | platform_resource_t aper; | |
375 | uint32_t apic_id; | |
376 | uint32_t msie; | |
377 | ringbuffer ringbuff[MIC_ENG_MAX_SUPPORTED_ENGINES]; | |
378 | uint32_t rb_readoff __attribute__((aligned(64))); | |
379 | micpm_ctx_t micpm_ctx; | |
380 | CARD_USAGE_MODE card_usage_mode; | |
381 | uint64_t adptr_base_pa; | |
382 | ||
383 | int32_t bi_id; | |
384 | mic_irq_t bi_irq; | |
385 | struct tasklet_struct bi_dpc; | |
386 | scifhost_info_t bi_scif; | |
387 | #ifdef USE_VCONSOLE | |
388 | micvcons_t bi_vcons; | |
389 | #endif | |
390 | void *bi_vethinfo; | |
391 | struct mic_psmi_ctx bi_psmi; | |
392 | struct pci_dev *bi_pdev; | |
393 | ||
394 | MIC_STATUS state; | |
395 | struct mutex state_lock; | |
396 | MIC_MODES mode; | |
397 | wait_queue_head_t resetwq; | |
398 | char *image; | |
399 | char *initramfs; | |
400 | struct timer_list boot_timer; | |
401 | unsigned long boot_start; | |
402 | struct work_struct boot_ws; | |
403 | ||
404 | struct workqueue_struct *resetworkq; | |
405 | struct work_struct resetwork; | |
406 | struct workqueue_struct *ioremapworkq; | |
407 | struct work_struct ioremapwork; | |
408 | wait_queue_head_t ioremapwq; | |
409 | uint32_t reset_count; | |
410 | ||
411 | atomic_t bi_irq_received; | |
412 | uint8_t bi_stepping; | |
413 | uint8_t bi_substepping; | |
414 | product_platform_t bi_platform; | |
415 | product_family_t bi_family; | |
416 | struct board_info *bd_info; | |
417 | sysfs_info_t sysfs_info; | |
418 | #if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,14,0)) | |
419 | struct kernfs_node *sysfs_state; | |
420 | #else | |
421 | struct sysfs_dirent *sysfs_state; | |
422 | #endif | |
423 | spinlock_t sysfs_lock; | |
424 | mic_dma_handle_t dma_handle; | |
425 | uint32_t boot_mem; | |
426 | mic_smpt_t *mic_smpt; | |
427 | spinlock_t smpt_lock; | |
428 | uint32_t sdbic1; | |
429 | int64_t etc_comp; | |
430 | spinlock_t ramoops_lock; | |
431 | void *ramoops_va[2]; | |
432 | int ramoops_size; | |
433 | dma_addr_t ramoops_pa[2]; | |
434 | struct proc_dir_entry *ramoops_dir; | |
435 | struct proc_dir_entry *vmcore_dir; | |
436 | /* | |
437 | * List representing chunks of contiguous memory areas and | |
438 | * their offsets in vmcore file. | |
439 | */ | |
440 | struct list_head vmcore_list; | |
441 | /* Stores the pointer to the buffer containing kernel elf core headers */ | |
442 | char *elfcorebuf; | |
443 | size_t elfcorebuf_sz; | |
444 | /* Total size of vmcore file. */ | |
445 | uint64_t vmcore_size; | |
446 | int crash_count; | |
447 | int boot_count; | |
448 | void *log_buf_addr; | |
449 | int *log_buf_len; | |
450 | char sku_name[SKU_NAME_LEN]; | |
451 | atomic_t disconn_rescnt; | |
452 | atomic_t gate_interrupt; | |
453 | uint16_t numa_node; | |
454 | } mic_ctx_t; | |
455 | ||
456 | ||
457 | typedef struct mic_irqhander { | |
458 | int (*ih_func)(mic_ctx_t *mic_ctx, int doorbell); | |
459 | struct list_head ih_list; | |
460 | char *ih_idstring; | |
461 | } mic_irqhandler_t; | |
462 | ||
463 | /* SKU related definitions and declarations */ | |
464 | #define MAX_DEV_IDS 16 | |
465 | typedef struct sku_info { | |
466 | uint32_t fuserev_low; | |
467 | uint32_t fuserev_high; | |
468 | uint32_t memsize; | |
469 | uint32_t memfreq; | |
470 | char sku_name[SKU_NAME_LEN]; | |
471 | struct list_head sku; | |
472 | } sku_info_t; | |
473 | ||
474 | int sku_create_node(uint32_t fuserev_low, | |
475 | uint32_t fuserev_high, uint32_t mem_size, | |
476 | uint32_t mem_freq, char *sku_name, | |
477 | sku_info_t ** newnode); | |
478 | ||
479 | int sku_build_table(void); | |
480 | void sku_destroy_table(void); | |
481 | int sku_find(mic_ctx_t *mic_ctx, uint32_t device_id); | |
482 | ||
483 | /* End SKU related definitions and declarations */ | |
484 | ||
485 | #define MIC_NUM_MSIX_ENTRIES 1 | |
486 | typedef struct mic_data { | |
487 | int32_t dd_numdevs; | |
488 | int32_t dd_inuse; | |
489 | #ifdef USE_VCONSOLE | |
490 | micvcons_port_t dd_ports[MAX_BOARD_SUPPORTED]; | |
491 | #endif | |
492 | struct board_info *dd_bi[MAX_BOARD_SUPPORTED]; | |
493 | struct list_head dd_bdlist; | |
494 | micscif_pm_t dd_pm; | |
495 | uint64_t sysram; | |
496 | struct fasync_struct *dd_fasync; | |
497 | struct list_head sku_table[MAX_DEV_IDS]; | |
498 | } mic_data_t; | |
499 | ||
500 | #include "mic_interrupts.h" | |
501 | extern mic_data_t mic_data; | |
502 | extern struct micscif_dev scif_dev[]; | |
503 | ||
504 | typedef struct acptboot_data { | |
505 | scif_epd_t listen_epd; | |
506 | uint16_t acptboot_pn; | |
507 | struct workqueue_struct *acptbootwq; | |
508 | struct work_struct acptbootwork; | |
509 | }acptboot_data_t; | |
510 | ||
511 | void acptboot_exit(void); | |
512 | int acptboot_init(void); | |
513 | void adapter_init(void); | |
514 | int adapter_isr(mic_ctx_t *mic_ctx); | |
515 | int adapter_imsr(mic_ctx_t *mic_ctx); | |
516 | int adapter_remove(mic_ctx_t *mic_ctx); | |
517 | int adapter_do_ioctl(uint32_t cmd, uint64_t arg); | |
518 | int adapter_stop_device(mic_ctx_t *mic_ctx, int wait_reset, int reattempt); | |
519 | int adapter_shutdown_device(mic_ctx_t *mic_ctx); | |
520 | void calculate_etc_compensation(mic_ctx_t *mic_ctx); | |
521 | int adapter_probe(mic_ctx_t *mic_ctx); | |
522 | int adapter_post_boot_device(mic_ctx_t *mic_ctx); | |
523 | int adapter_start_device(mic_ctx_t *mic_ctx); | |
524 | int adapter_restart_device(mic_ctx_t *mic_ctx); | |
525 | int adapter_init_device(mic_ctx_t *mic_ctx); | |
526 | int pm_adapter_do_ioctl(mic_ctx_t *mic_ctx, void *in_buffer); | |
527 | int adapter_reset_depgraph(mic_ctx_t *mic_ctx); | |
528 | ||
529 | /* | |
530 | * RESET_WAIT : launch the timer thread and wait for reset to complete | |
531 | * The caller has to add itself to the resetwq by calling wait_for_reset | |
532 | * RESET_REATTEMPT : Reattempt reset after detecting failures in reset | |
533 | */ | |
534 | #define RESET_WAIT 1 | |
535 | #define RESET_REATTEMPT 1 | |
536 | void adapter_reset(mic_ctx_t *mic_ctx, int wait_reset, int reattempt); | |
537 | ||
538 | void adapter_wait_reset(mic_ctx_t *mic_ctx); | |
539 | void get_adapter_memsize(uint8_t *mmio_va, uint32_t *adapter_mem_size); | |
540 | int wait_for_bootstrap(uint8_t *mmio_va); | |
541 | void post_boot_startup(struct work_struct *work); | |
542 | void attempt_reset(struct work_struct *work); | |
543 | ||
544 | int send_uos_escape(mic_ctx_t *mic_ctx, uint32_t uos_op, | |
545 | uint32_t data_size, void *escape_data); | |
546 | int boot_linux_uos(mic_ctx_t *mic_ctx, char *imgname, char *initramfsname); | |
547 | ||
548 | int boot_micdev_app(mic_ctx_t *mic_ctx, char *imgname); | |
549 | int allocate_tools_buffer(mic_ctx_t *mic_ctx, uint32_t databuf_size, | |
550 | uint32_t stsbuf_size, uint64_t *gddr_data_ptr, | |
551 | uint64_t *gddr_stsbuf_ptr); | |
552 | ||
553 | int micpm_init(void); | |
554 | void micpm_uninit(void); | |
555 | int micpm_stop(mic_ctx_t *mic_ctx); | |
556 | int micpm_start(mic_ctx_t *mic_ctx); | |
557 | int micpm_probe(mic_ctx_t *mic_ctx); | |
558 | int micpm_remove(mic_ctx_t *mic_ctx); | |
559 | void micpm_nodemask_uninit(mic_ctx_t* mic_ctx); | |
560 | int micpm_nodemask_init(uint32_t num_devs, mic_ctx_t* mic_ctx); | |
561 | int micpm_disconn_init(uint32_t num_nodes); | |
562 | int micpm_disconn_uninit(uint32_t num_nodes); | |
563 | int micpm_dbg_init(mic_ctx_t *mic_ctx); | |
564 | void micpm_dbg_parent_init(void); | |
565 | int pm_reg_read(mic_ctx_t *mic_ctx, uint32_t regoffset); | |
566 | int micpm_update_pc6(mic_ctx_t *mic_ctx, bool set); | |
567 | int micpm_update_pc3(mic_ctx_t *mic_ctx, bool set); | |
568 | int pm_start_device(mic_ctx_t *mic_ctx); | |
569 | int pm_stop_device(mic_ctx_t *mic_ctx); | |
570 | int mic_pm_recv(mic_ctx_t *mic_ctx, void *msg, uint32_t len); | |
571 | int mic_pm_send_msg(mic_ctx_t *mic_ctx, PM_MESSAGE type, | |
572 | void *msg, uint32_t len); | |
573 | ||
574 | int pm_pc3_entry(mic_ctx_t *mic_ctx); | |
575 | int pm_pc3_exit(mic_ctx_t *mic_ctx); | |
576 | int do_idlestate_entry(mic_ctx_t *mic_ctx); | |
577 | int do_idlestate_exit(mic_ctx_t *mic_ctx, bool get_ref); | |
578 | int is_idlestate_exit_needed(mic_ctx_t *mic_ctx); | |
579 | uint32_t mic_get_scifnode_id(mic_ctx_t *mic_ctx); | |
580 | ||
581 | mic_ctx_t* get_per_dev_ctx(uint16_t node); | |
582 | int get_num_devs(mic_ctx_t *mic_ctx, uint32_t *num_devs); | |
583 | ||
584 | ||
585 | void adapter_uninit(void); | |
586 | void adapter_add(mic_ctx_t *mic_ctx); | |
587 | void adapter_start(mic_ctx_t *mic_ctx); | |
588 | int send_flash_cmd(mic_ctx_t *mic_ctx, MIC_FLASH_CMD_TYPE type, void *data, | |
589 | uint32_t len); | |
590 | int cmdline_mem(mic_ctx_t *mic_ctx, uint32_t mem); | |
591 | int get_cardside_mem(mic_ctx_t *mic_ctx, uint64_t start, uint64_t size, void *dest); | |
592 | ||
593 | int mic_pin_user_pages (void *data, struct page **pages, uint32_t len, int32_t *nf_pages, int32_t nr_pages); | |
594 | int mic_unpin_user_pages(struct page **pages, uint32_t nf_pages); | |
595 | product_family_t get_product_family(uint32_t device_id); | |
596 | void show_stepping_comm(mic_ctx_t *mic_ctx,char *buf); | |
597 | void micscif_destroy_p2p(mic_ctx_t *mic_ctx); | |
598 | ||
599 | #ifdef HOST | |
600 | void mic_smpt_init(mic_ctx_t *mic_ctx); | |
601 | void mic_smpt_restore(mic_ctx_t *mic_ctx); | |
602 | #endif | |
603 | void mic_smpt_uninit(mic_ctx_t *mic_ctx); | |
604 | int mic_dma_init(void); | |
605 | ||
606 | #ifndef _MIC_SCIF_ | |
607 | static __always_inline int micpm_get_reference(mic_ctx_t *mic_ctx, bool force_wakeup) { | |
608 | int err; | |
609 | if (!mic_ctx) | |
610 | return -EINVAL; | |
611 | ||
612 | if (mic_ctx->micpm_ctx.idle_state == PM_IDLE_STATE_LOST) | |
613 | return -ENODEV; | |
614 | ||
615 | if (unlikely(!atomic_add_unless(&mic_ctx->micpm_ctx.pm_ref_cnt, | |
616 | 1, PM_NODE_IDLE))) { | |
617 | if (!force_wakeup) { | |
618 | if (is_idlestate_exit_needed(mic_ctx)) { | |
619 | return -EAGAIN; | |
620 | } | |
621 | } | |
622 | ||
623 | if ((err = micscif_connect_node(mic_get_scifnode_id(mic_ctx), true)) != 0) | |
624 | return -ENODEV; | |
625 | } | |
626 | return 0; | |
627 | } | |
628 | #endif | |
629 | ||
630 | static __always_inline int micpm_put_reference(mic_ctx_t *mic_ctx) { | |
631 | int ret; | |
632 | ||
633 | if(!mic_ctx) | |
634 | return -EINVAL; | |
635 | ||
636 | if (mic_ctx->micpm_ctx.idle_state == PM_IDLE_STATE_LOST) | |
637 | return -ENODEV; | |
638 | ||
639 | if (unlikely((ret = atomic_sub_return(1, | |
640 | &mic_ctx->micpm_ctx.pm_ref_cnt)) < 0)) { | |
641 | printk(KERN_ERR "%s %d Invalid PM ref_cnt %d \n", | |
642 | __func__, __LINE__, atomic_read(&mic_ctx->micpm_ctx.pm_ref_cnt)); | |
643 | } | |
644 | ||
645 | return 0; | |
646 | ||
647 | } | |
648 | ||
649 | static __always_inline int | |
650 | mic_hw_family(int node_id) { | |
651 | mic_ctx_t *mic_ctx; | |
652 | ||
653 | /* For Host Loopback */ | |
654 | if (!node_id) | |
655 | return -EINVAL; | |
656 | ||
657 | mic_ctx = get_per_dev_ctx(node_id - 1); | |
658 | return mic_ctx->bi_family; | |
659 | } | |
660 | ||
661 | static __always_inline void | |
662 | wait_for_reset(mic_ctx_t *mic_ctx) | |
663 | { | |
664 | int ret = 0; | |
665 | while (!ret) { | |
666 | ret = wait_event_timeout(mic_ctx->resetwq, | |
667 | mic_ctx->state != MIC_RESET, RESET_FAIL_TIME * HZ); | |
668 | } | |
669 | } | |
670 | ||
671 | /* Called only by host PM suspend */ | |
672 | static __always_inline int | |
673 | wait_for_shutdown_and_reset(mic_ctx_t *mic_ctx) | |
674 | { | |
675 | int ret; | |
676 | ret = wait_event_interruptible_timeout(mic_ctx->resetwq, | |
677 | mic_ctx->state != MIC_RESET && mic_ctx->state != MIC_SHUTDOWN, | |
678 | RESET_FAIL_TIME * HZ); | |
679 | return ret; | |
680 | } | |
681 | ||
682 | static __always_inline void | |
683 | mic_signal_daemon(void) | |
684 | { | |
685 | if (mic_data.dd_fasync != NULL) | |
686 | kill_fasync(&mic_data.dd_fasync, SIGIO, POLL_IN); | |
687 | } | |
688 | ||
689 | extern char *micstates[]; | |
690 | ||
691 | #if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,10,0)) | |
692 | #define __mic_create_singlethread_workqueue(name) alloc_ordered_workqueue(name, 0) | |
693 | #else | |
694 | #define __mic_create_singlethread_workqueue(name) create_singlethread_workqueue(name) | |
695 | #endif | |
696 | ||
697 | static __always_inline void | |
698 | mic_setstate(mic_ctx_t *mic_ctx, enum mic_status newstate) | |
699 | { | |
700 | printk("mic%d: Transition from state %s to %s\n", mic_ctx->bi_id, | |
701 | micstates[mic_ctx->state], micstates[newstate]); | |
702 | mic_ctx->state = newstate; | |
703 | spin_lock_bh(&mic_ctx->sysfs_lock); | |
704 | if (mic_ctx->sysfs_state) | |
705 | sysfs_notify_dirent(mic_ctx->sysfs_state); | |
706 | spin_unlock_bh(&mic_ctx->sysfs_lock); | |
707 | } | |
708 | ||
709 | #define MICREG_POSTCODE 0x242c | |
710 | ||
711 | static __always_inline uint32_t | |
712 | mic_getpostcode(mic_ctx_t *mic_ctx) | |
713 | { | |
714 | return DBOX_READ(mic_ctx->mmio.va, MICREG_POSTCODE); | |
715 | } | |
716 | ||
717 | static __always_inline int | |
718 | mic_hw_stepping(int node_id) { | |
719 | mic_ctx_t *mic_ctx; | |
720 | ||
721 | /* For Host Loopback */ | |
722 | if (!node_id) | |
723 | return -EINVAL; | |
724 | ||
725 | mic_ctx = get_per_dev_ctx(node_id - 1); | |
726 | return mic_ctx->bi_stepping; | |
727 | } | |
728 | ||
729 | #define MIC_IRQ_DB0 0 | |
730 | #define MIC_IRQ_DB1 1 | |
731 | #define MIC_IRQ_DB2 2 | |
732 | #define MIC_IRQ_DB3 3 | |
733 | #define MIC_IRQ_MAX MIC_IRQ_DB3 | |
734 | ||
735 | int mic_reg_irqhandler(mic_ctx_t *mic_ctx, int doorbell, char *idstring, | |
736 | int (*irqfunc)(mic_ctx_t *mic_ctx, int doorbell)); | |
737 | int mic_unreg_irqhandler(mic_ctx_t *mic_ctx, int doorbell, char *idstring); | |
738 | void mic_enable_interrupts(mic_ctx_t *mic_ctx); | |
739 | void mic_disable_interrupts(mic_ctx_t *mic_ctx); | |
740 | void mic_enable_msi_interrupts(mic_ctx_t *mic_ctx); | |
741 | ||
742 | int micscif_init(void); | |
743 | void micscif_destroy(void); | |
744 | void micscif_probe(mic_ctx_t *mic_ctx); | |
745 | void micscif_remove(mic_ctx_t *mic_ctx); | |
746 | void micscif_start(mic_ctx_t *mic_ctx); | |
747 | void micscif_stop(mic_ctx_t *mic_ctx); | |
748 | ||
749 | mic_ctx_t *get_device_context(struct pci_dev *dev); | |
750 | void ramoops_exit(void); | |
751 | void vmcore_exit(void); | |
752 | int vmcore_create(mic_ctx_t *mic_ctx); | |
753 | void vmcore_remove(mic_ctx_t *mic_ctx); | |
754 | ||
755 | // loads file into memory | |
756 | int mic_get_file_size(const char *path, uint32_t *file_length); | |
757 | int mic_load_file(const char *fn, uint8_t *buffer, uint32_t max_size); | |
758 | #ifndef _MIC_SCIF_ | |
759 | void mic_debug_init(mic_ctx_t *mic_ctx); | |
760 | #endif | |
761 | void mic_debug_uninit(void); | |
762 | void | |
763 | set_pci_aperture(mic_ctx_t *mic_ctx, uint32_t gtt_index, uint64_t phy_addr, uint32_t num_bytes); | |
764 | #ifdef __cplusplus | |
765 | }; | |
766 | #endif | |
767 | ||
768 | #endif // __MIC_COMMON_H | |
769 |