Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
openanolis
cloud-kernel
提交
8206ceb0
cloud-kernel
项目概览
openanolis
/
cloud-kernel
接近 2 年 前同步成功
通知
170
Star
36
Fork
7
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
10
列表
看板
标记
里程碑
合并请求
2
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
cloud-kernel
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
10
Issue
10
列表
看板
标记
里程碑
合并请求
2
合并请求
2
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
提交
8206ceb0
编写于
9月 29, 2017
作者:
D
Doug Ledford
浏览文件
操作
浏览文件
下载
差异文件
Merge branch 'hfi1' into k.o/for-next
Signed-off-by:
N
Doug Ledford
<
dledford@redhat.com
>
上级
1848757c
ecf79985
变更
20
展开全部
隐藏空白更改
内联
并排
Showing
20 changed file
with
577 addition
and
627 deletion
+577
-627
drivers/infiniband/hw/hfi1/chip.c
drivers/infiniband/hw/hfi1/chip.c
+28
-42
drivers/infiniband/hw/hfi1/debugfs.c
drivers/infiniband/hw/hfi1/debugfs.c
+2
-2
drivers/infiniband/hw/hfi1/driver.c
drivers/infiniband/hw/hfi1/driver.c
+2
-2
drivers/infiniband/hw/hfi1/file_ops.c
drivers/infiniband/hw/hfi1/file_ops.c
+280
-204
drivers/infiniband/hw/hfi1/hfi.h
drivers/infiniband/hw/hfi1/hfi.h
+11
-7
drivers/infiniband/hw/hfi1/init.c
drivers/infiniband/hw/hfi1/init.c
+21
-22
drivers/infiniband/hw/hfi1/sdma.c
drivers/infiniband/hw/hfi1/sdma.c
+7
-7
drivers/infiniband/hw/hfi1/trace.c
drivers/infiniband/hw/hfi1/trace.c
+10
-13
drivers/infiniband/hw/hfi1/trace.h
drivers/infiniband/hw/hfi1/trace.h
+10
-0
drivers/infiniband/hw/hfi1/trace_ibhdrs.h
drivers/infiniband/hw/hfi1/trace_ibhdrs.h
+23
-21
drivers/infiniband/hw/hfi1/trace_rx.h
drivers/infiniband/hw/hfi1/trace_rx.h
+1
-10
drivers/infiniband/hw/hfi1/user_exp_rcv.c
drivers/infiniband/hw/hfi1/user_exp_rcv.c
+2
-7
drivers/infiniband/hw/hfi1/user_sdma.c
drivers/infiniband/hw/hfi1/user_sdma.c
+40
-22
drivers/infiniband/hw/hfi1/user_sdma.h
drivers/infiniband/hw/hfi1/user_sdma.h
+20
-9
drivers/infiniband/hw/qib/qib.h
drivers/infiniband/hw/qib/qib.h
+2
-6
drivers/infiniband/hw/qib/qib_7220.h
drivers/infiniband/hw/qib/qib_7220.h
+0
-1
drivers/infiniband/hw/qib/qib_iba6120.c
drivers/infiniband/hw/qib/qib_iba6120.c
+9
-26
drivers/infiniband/hw/qib/qib_iba7220.c
drivers/infiniband/hw/qib/qib_iba7220.c
+15
-37
drivers/infiniband/hw/qib/qib_iba7322.c
drivers/infiniband/hw/qib/qib_iba7322.c
+62
-96
drivers/infiniband/hw/qib/qib_pcie.c
drivers/infiniband/hw/qib/qib_pcie.c
+32
-93
未找到文件。
drivers/infiniband/hw/hfi1/chip.c
浏览文件 @
8206ceb0
...
...
@@ -9956,7 +9956,7 @@ int hfi1_get_ib_cfg(struct hfi1_pportdata *ppd, int which)
val
=
ppd
->
phy_error_threshold
;
break
;
case
HFI1_IB_CFG_LINKDEFAULT
:
/* IB link default (sleep/poll) */
val
=
dd
->
link_default
;
val
=
HLS_DEFAULT
;
break
;
case
HFI1_IB_CFG_HRTBT
:
/* Heartbeat off/enable/auto */
...
...
@@ -10159,6 +10159,10 @@ static const char * const state_complete_reasons[] = {
[
0x33
]
=
"Link partner completed the VerifyCap state, but the passing lanes do not meet the local link width policy"
,
[
0x34
]
=
tx_out_of_policy
,
[
0x35
]
=
"Negotiated link width is mutually exclusive"
,
[
0x36
]
=
"Timed out before receiving verifycap frames in VerifyCap.Exchange"
,
[
0x37
]
=
"Unable to resolve secure data exchange"
,
};
static
const
char
*
state_complete_reason_code_string
(
struct
hfi1_pportdata
*
ppd
,
...
...
@@ -10547,7 +10551,7 @@ int set_link_state(struct hfi1_pportdata *ppd, u32 state)
orig_new_state
=
state
;
if
(
state
==
HLS_DN_DOWNDEF
)
state
=
dd
->
link_default
;
state
=
HLS_DEFAULT
;
/* interpret poll -> poll as a link bounce */
poll_bounce
=
ppd
->
host_link_state
==
HLS_DN_POLL
&&
...
...
@@ -12925,7 +12929,7 @@ static void clean_up_interrupts(struct hfi1_devdata *dd)
if
(
!
me
->
arg
)
/* => no irq, no affinity */
continue
;
hfi1_put_irq_affinity
(
dd
,
me
);
free_irq
(
me
->
irq
,
me
->
arg
);
pci_free_irq
(
dd
->
pcidev
,
i
,
me
->
arg
);
}
/* clean structures */
...
...
@@ -12935,7 +12939,7 @@ static void clean_up_interrupts(struct hfi1_devdata *dd)
}
else
{
/* INTx */
if
(
dd
->
requested_intx_irq
)
{
free_irq
(
dd
->
pcidev
->
irq
,
dd
);
pci_free_irq
(
dd
->
pcidev
,
0
,
dd
);
dd
->
requested_intx_irq
=
0
;
}
disable_intx
(
dd
->
pcidev
);
...
...
@@ -12994,10 +12998,8 @@ static int request_intx_irq(struct hfi1_devdata *dd)
{
int
ret
;
snprintf
(
dd
->
intx_name
,
sizeof
(
dd
->
intx_name
),
DRIVER_NAME
"_%d"
,
dd
->
unit
);
ret
=
request_irq
(
dd
->
pcidev
->
irq
,
general_interrupt
,
IRQF_SHARED
,
dd
->
intx_name
,
dd
);
ret
=
pci_request_irq
(
dd
->
pcidev
,
0
,
general_interrupt
,
NULL
,
dd
,
DRIVER_NAME
"_%d"
,
dd
->
unit
);
if
(
ret
)
dd_dev_err
(
dd
,
"unable to request INTx interrupt, err %d
\n
"
,
ret
);
...
...
@@ -13040,13 +13042,14 @@ static int request_msix_irqs(struct hfi1_devdata *dd)
int
idx
;
struct
hfi1_ctxtdata
*
rcd
=
NULL
;
struct
sdma_engine
*
sde
=
NULL
;
char
name
[
MAX_NAME_SIZE
];
/* obtain the arguments to request_irq */
/* obtain the arguments to
pci_
request_irq */
if
(
first_general
<=
i
&&
i
<
last_general
)
{
idx
=
i
-
first_general
;
handler
=
general_interrupt
;
arg
=
dd
;
snprintf
(
me
->
name
,
sizeof
(
me
->
name
),
snprintf
(
name
,
sizeof
(
name
),
DRIVER_NAME
"_%d"
,
dd
->
unit
);
err_info
=
"general"
;
me
->
type
=
IRQ_GENERAL
;
...
...
@@ -13055,14 +13058,14 @@ static int request_msix_irqs(struct hfi1_devdata *dd)
sde
=
&
dd
->
per_sdma
[
idx
];
handler
=
sdma_interrupt
;
arg
=
sde
;
snprintf
(
me
->
name
,
sizeof
(
me
->
name
),
snprintf
(
name
,
sizeof
(
name
),
DRIVER_NAME
"_%d sdma%d"
,
dd
->
unit
,
idx
);
err_info
=
"sdma"
;
remap_sdma_interrupts
(
dd
,
idx
,
i
);
me
->
type
=
IRQ_SDMA
;
}
else
if
(
first_rx
<=
i
&&
i
<
last_rx
)
{
idx
=
i
-
first_rx
;
rcd
=
hfi1_rcd_get_by_index
(
dd
,
idx
);
rcd
=
hfi1_rcd_get_by_index
_safe
(
dd
,
idx
);
if
(
rcd
)
{
/*
* Set the interrupt register and mask for this
...
...
@@ -13074,7 +13077,7 @@ static int request_msix_irqs(struct hfi1_devdata *dd)
handler
=
receive_context_interrupt
;
thread
=
receive_context_thread
;
arg
=
rcd
;
snprintf
(
me
->
name
,
sizeof
(
me
->
name
),
snprintf
(
name
,
sizeof
(
name
),
DRIVER_NAME
"_%d kctxt%d"
,
dd
->
unit
,
idx
);
err_info
=
"receive context"
;
...
...
@@ -13095,18 +13098,10 @@ static int request_msix_irqs(struct hfi1_devdata *dd)
if
(
!
arg
)
continue
;
/* make sure the name is terminated */
me
->
name
[
sizeof
(
me
->
name
)
-
1
]
=
0
;
name
[
sizeof
(
name
)
-
1
]
=
0
;
me
->
irq
=
pci_irq_vector
(
dd
->
pcidev
,
i
);
/*
* On err return me->irq. Don't need to clear this
* because 'arg' has not been set, and cleanup will
* do the right thing.
*/
if
(
me
->
irq
<
0
)
return
me
->
irq
;
ret
=
request_threaded_irq
(
me
->
irq
,
handler
,
thread
,
0
,
me
->
name
,
arg
);
ret
=
pci_request_irq
(
dd
->
pcidev
,
i
,
handler
,
thread
,
arg
,
name
);
if
(
ret
)
{
dd_dev_err
(
dd
,
"unable to allocate %s interrupt, irq %d, index %d, err %d
\n
"
,
...
...
@@ -13114,7 +13109,7 @@ static int request_msix_irqs(struct hfi1_devdata *dd)
return
ret
;
}
/*
* assign arg after request_irq call, so it will be
* assign arg after
pci_
request_irq call, so it will be
* cleaned up
*/
me
->
arg
=
arg
;
...
...
@@ -13132,7 +13127,7 @@ void hfi1_vnic_synchronize_irq(struct hfi1_devdata *dd)
int
i
;
if
(
!
dd
->
num_msix_entries
)
{
synchronize_irq
(
dd
->
pcidev
->
irq
);
synchronize_irq
(
pci_irq_vector
(
dd
->
pcidev
,
0
)
);
return
;
}
...
...
@@ -13153,7 +13148,7 @@ void hfi1_reset_vnic_msix_info(struct hfi1_ctxtdata *rcd)
return
;
hfi1_put_irq_affinity
(
dd
,
me
);
free_irq
(
me
->
irq
,
me
->
arg
);
pci_free_irq
(
dd
->
pcidev
,
rcd
->
msix_intr
,
me
->
arg
);
me
->
arg
=
NULL
;
}
...
...
@@ -13176,28 +13171,21 @@ void hfi1_set_vnic_msix_info(struct hfi1_ctxtdata *rcd)
rcd
->
ireg
=
(
IS_RCVAVAIL_START
+
idx
)
/
64
;
rcd
->
imask
=
((
u64
)
1
)
<<
((
IS_RCVAVAIL_START
+
idx
)
%
64
);
snprintf
(
me
->
name
,
sizeof
(
me
->
name
),
DRIVER_NAME
"_%d kctxt%d"
,
dd
->
unit
,
idx
);
me
->
name
[
sizeof
(
me
->
name
)
-
1
]
=
0
;
me
->
type
=
IRQ_RCVCTXT
;
me
->
irq
=
pci_irq_vector
(
dd
->
pcidev
,
rcd
->
msix_intr
);
if
(
me
->
irq
<
0
)
{
dd_dev_err
(
dd
,
"vnic irq vector request (idx %d) fail %d
\n
"
,
idx
,
me
->
irq
);
return
;
}
remap_intr
(
dd
,
IS_RCVAVAIL_START
+
idx
,
rcd
->
msix_intr
);
ret
=
request_threaded_irq
(
me
->
irq
,
receive_context_interrupt
,
receive_context_thread
,
0
,
me
->
name
,
arg
);
ret
=
pci_request_irq
(
dd
->
pcidev
,
rcd
->
msix_intr
,
receive_context_interrupt
,
receive_context_thread
,
arg
,
DRIVER_NAME
"_%d kctxt%d"
,
dd
->
unit
,
idx
);
if
(
ret
)
{
dd_dev_err
(
dd
,
"vnic irq request (irq %d, idx %d) fail %d
\n
"
,
me
->
irq
,
idx
,
ret
);
return
;
}
/*
* assign arg after request_irq call, so it will be
* assign arg after
pci_
request_irq call, so it will be
* cleaned up
*/
me
->
arg
=
arg
;
...
...
@@ -13206,7 +13194,7 @@ void hfi1_set_vnic_msix_info(struct hfi1_ctxtdata *rcd)
if
(
ret
)
{
dd_dev_err
(
dd
,
"unable to pin IRQ %d
\n
"
,
ret
);
free_irq
(
me
->
irq
,
me
->
arg
);
pci_free_irq
(
dd
->
pcidev
,
rcd
->
msix_intr
,
me
->
arg
);
}
}
...
...
@@ -14907,8 +14895,6 @@ struct hfi1_devdata *hfi1_init_dd(struct pci_dev *pdev,
init_vl_arb_caches
(
ppd
);
}
dd
->
link_default
=
HLS_DN_POLL
;
/*
* Do remaining PCIe setup and save PCIe values in dd.
* Any error printing is already done by the init code.
...
...
drivers/infiniband/hw/hfi1/debugfs.c
浏览文件 @
8206ceb0
...
...
@@ -243,7 +243,7 @@ static int _ctx_stats_seq_show(struct seq_file *s, void *v)
spos
=
v
;
i
=
*
spos
;
rcd
=
hfi1_rcd_get_by_index
(
dd
,
i
);
rcd
=
hfi1_rcd_get_by_index
_safe
(
dd
,
i
);
if
(
!
rcd
)
return
SEQ_SKIP
;
...
...
@@ -402,7 +402,7 @@ static int _rcds_seq_show(struct seq_file *s, void *v)
loff_t
*
spos
=
v
;
loff_t
i
=
*
spos
;
rcd
=
hfi1_rcd_get_by_index
(
dd
,
i
);
rcd
=
hfi1_rcd_get_by_index
_safe
(
dd
,
i
);
if
(
rcd
)
seqfile_dump_rcd
(
s
,
rcd
);
hfi1_rcd_put
(
rcd
);
...
...
drivers/infiniband/hw/hfi1/driver.c
浏览文件 @
8206ceb0
...
...
@@ -866,7 +866,7 @@ static inline void set_nodma_rtail(struct hfi1_devdata *dd, u16 ctxt)
* interrupt handler for all statically allocated kernel contexts.
*/
if
(
ctxt
>=
dd
->
first_dyn_alloc_ctxt
)
{
rcd
=
hfi1_rcd_get_by_index
(
dd
,
ctxt
);
rcd
=
hfi1_rcd_get_by_index
_safe
(
dd
,
ctxt
);
if
(
rcd
)
{
rcd
->
do_interrupt
=
&
handle_receive_interrupt_nodma_rtail
;
...
...
@@ -895,7 +895,7 @@ static inline void set_dma_rtail(struct hfi1_devdata *dd, u16 ctxt)
* interrupt handler for all statically allocated kernel contexts.
*/
if
(
ctxt
>=
dd
->
first_dyn_alloc_ctxt
)
{
rcd
=
hfi1_rcd_get_by_index
(
dd
,
ctxt
);
rcd
=
hfi1_rcd_get_by_index
_safe
(
dd
,
ctxt
);
if
(
rcd
)
{
rcd
->
do_interrupt
=
&
handle_receive_interrupt_dma_rtail
;
...
...
drivers/infiniband/hw/hfi1/file_ops.c
浏览文件 @
8206ceb0
此差异已折叠。
点击以展开。
drivers/infiniband/hw/hfi1/hfi.h
浏览文件 @
8206ceb0
...
...
@@ -535,6 +535,8 @@ struct rvt_sge_state;
#define HLS_UP (HLS_UP_INIT | HLS_UP_ARMED | HLS_UP_ACTIVE)
#define HLS_DOWN ~(HLS_UP)
#define HLS_DEFAULT HLS_DN_POLL
/* use this MTU size if none other is given */
#define HFI1_DEFAULT_ACTIVE_MTU 10240
/* use this MTU size as the default maximum */
...
...
@@ -616,7 +618,6 @@ struct hfi1_msix_entry {
enum
irq_type
type
;
int
irq
;
void
*
arg
;
char
name
[
MAX_NAME_SIZE
];
cpumask_t
mask
;
struct
irq_affinity_notify
notify
;
};
...
...
@@ -1109,8 +1110,7 @@ struct hfi1_devdata {
u16
rcvegrbufsize_shift
;
/* both sides of the PCIe link are gen3 capable */
u8
link_gen3_capable
;
/* default link down value (poll/sleep) */
u8
link_default
;
u8
dc_shutdown
;
/* localbus width (1, 2,4,8,16,32) from config space */
u32
lbus_width
;
/* localbus speed in MHz */
...
...
@@ -1183,7 +1183,6 @@ struct hfi1_devdata {
/* INTx information */
u32
requested_intx_irq
;
/* did we request one? */
char
intx_name
[
MAX_NAME_SIZE
];
/* INTx name */
/* general interrupt: mask of handled interrupts */
u64
gi_mask
[
CCE_NUM_INT_CSRS
];
...
...
@@ -1295,7 +1294,6 @@ struct hfi1_devdata {
u8
oui1
;
u8
oui2
;
u8
oui3
;
u8
dc_shutdown
;
/* Timer and counter used to detect RcvBufOvflCnt changes */
struct
timer_list
rcverr_timer
;
...
...
@@ -1373,8 +1371,12 @@ struct hfi1_filedata {
extern
struct
list_head
hfi1_dev_list
;
extern
spinlock_t
hfi1_devs_lock
;
struct
hfi1_devdata
*
hfi1_lookup
(
int
unit
);
extern
u32
hfi1_cpulist_count
;
extern
unsigned
long
*
hfi1_cpulist
;
static
inline
unsigned
long
uctxt_offset
(
struct
hfi1_ctxtdata
*
uctxt
)
{
return
(
uctxt
->
ctxt
-
uctxt
->
dd
->
first_dyn_alloc_ctxt
)
*
HFI1_MAX_SHARED_CTXTS
;
}
int
hfi1_init
(
struct
hfi1_devdata
*
dd
,
int
reinit
);
int
hfi1_count_active_units
(
void
);
...
...
@@ -1396,6 +1398,8 @@ void hfi1_init_pportdata(struct pci_dev *pdev, struct hfi1_pportdata *ppd,
void
hfi1_free_ctxtdata
(
struct
hfi1_devdata
*
dd
,
struct
hfi1_ctxtdata
*
rcd
);
int
hfi1_rcd_put
(
struct
hfi1_ctxtdata
*
rcd
);
void
hfi1_rcd_get
(
struct
hfi1_ctxtdata
*
rcd
);
struct
hfi1_ctxtdata
*
hfi1_rcd_get_by_index_safe
(
struct
hfi1_devdata
*
dd
,
u16
ctxt
);
struct
hfi1_ctxtdata
*
hfi1_rcd_get_by_index
(
struct
hfi1_devdata
*
dd
,
u16
ctxt
);
int
handle_receive_interrupt
(
struct
hfi1_ctxtdata
*
rcd
,
int
thread
);
int
handle_receive_interrupt_nodma_rtail
(
struct
hfi1_ctxtdata
*
rcd
,
int
thread
);
...
...
drivers/infiniband/hw/hfi1/init.c
浏览文件 @
8206ceb0
...
...
@@ -123,8 +123,6 @@ MODULE_PARM_DESC(user_credit_return_threshold, "Credit return threshold for user
static
inline
u64
encode_rcv_header_entry_size
(
u16
size
);
static
struct
idr
hfi1_unit_table
;
u32
hfi1_cpulist_count
;
unsigned
long
*
hfi1_cpulist
;
static
int
hfi1_create_kctxt
(
struct
hfi1_devdata
*
dd
,
struct
hfi1_pportdata
*
ppd
)
...
...
@@ -285,6 +283,27 @@ static int allocate_rcd_index(struct hfi1_devdata *dd,
return
0
;
}
/**
* hfi1_rcd_get_by_index_safe - validate the ctxt index before accessing the
* array
* @dd: pointer to a valid devdata structure
* @ctxt: the index of an possilbe rcd
*
* This is a wrapper for hfi1_rcd_get_by_index() to validate that the given
* ctxt index is valid.
*
* The caller is responsible for making the _put().
*
*/
struct
hfi1_ctxtdata
*
hfi1_rcd_get_by_index_safe
(
struct
hfi1_devdata
*
dd
,
u16
ctxt
)
{
if
(
ctxt
<
dd
->
num_rcv_contexts
)
return
hfi1_rcd_get_by_index
(
dd
,
ctxt
);
return
NULL
;
}
/**
* hfi1_rcd_get_by_index
* @dd: pointer to a valid devdata structure
...
...
@@ -1272,39 +1291,21 @@ struct hfi1_devdata *hfi1_alloc_devdata(struct pci_dev *pdev, size_t extra)
dd
->
int_counter
=
alloc_percpu
(
u64
);
if
(
!
dd
->
int_counter
)
{
ret
=
-
ENOMEM
;
hfi1_early_err
(
&
pdev
->
dev
,
"Could not allocate per-cpu int_counter
\n
"
);
goto
bail
;
}
dd
->
rcv_limit
=
alloc_percpu
(
u64
);
if
(
!
dd
->
rcv_limit
)
{
ret
=
-
ENOMEM
;
hfi1_early_err
(
&
pdev
->
dev
,
"Could not allocate per-cpu rcv_limit
\n
"
);
goto
bail
;
}
dd
->
send_schedule
=
alloc_percpu
(
u64
);
if
(
!
dd
->
send_schedule
)
{
ret
=
-
ENOMEM
;
hfi1_early_err
(
&
pdev
->
dev
,
"Could not allocate per-cpu int_counter
\n
"
);
goto
bail
;
}
if
(
!
hfi1_cpulist_count
)
{
u32
count
=
num_online_cpus
();
hfi1_cpulist
=
kcalloc
(
BITS_TO_LONGS
(
count
),
sizeof
(
long
),
GFP_KERNEL
);
if
(
hfi1_cpulist
)
hfi1_cpulist_count
=
count
;
else
hfi1_early_err
(
&
pdev
->
dev
,
"Could not alloc cpulist info, cpu affinity might be wrong
\n
"
);
}
kobject_init
(
&
dd
->
kobj
,
&
hfi1_devdata_type
);
return
dd
;
...
...
@@ -1477,8 +1478,6 @@ static void __exit hfi1_mod_cleanup(void)
node_affinity_destroy
();
hfi1_wss_exit
();
hfi1_dbg_exit
();
hfi1_cpulist_count
=
0
;
kfree
(
hfi1_cpulist
);
idr_destroy
(
&
hfi1_unit_table
);
dispose_firmware
();
/* asymmetric with obtain_firmware() */
...
...
drivers/infiniband/hw/hfi1/sdma.c
浏览文件 @
8206ceb0
...
...
@@ -1392,6 +1392,13 @@ int sdma_init(struct hfi1_devdata *dd, u8 port)
return
ret
;
idle_cnt
=
ns_to_cclock
(
dd
,
idle_cnt
);
if
(
idle_cnt
)
dd
->
default_desc1
=
SDMA_DESC1_HEAD_TO_HOST_FLAG
;
else
dd
->
default_desc1
=
SDMA_DESC1_INT_REQ_FLAG
;
if
(
!
sdma_desct_intr
)
sdma_desct_intr
=
SDMA_DESC_INTR
;
...
...
@@ -1436,13 +1443,6 @@ int sdma_init(struct hfi1_devdata *dd, u8 port)
sde
->
tail_csr
=
get_kctxt_csr_addr
(
dd
,
this_idx
,
SD
(
TAIL
));
if
(
idle_cnt
)
dd
->
default_desc1
=
SDMA_DESC1_HEAD_TO_HOST_FLAG
;
else
dd
->
default_desc1
=
SDMA_DESC1_INT_REQ_FLAG
;
tasklet_init
(
&
sde
->
sdma_hw_clean_up_task
,
sdma_hw_clean_up_task
,
(
unsigned
long
)
sde
);
...
...
drivers/infiniband/hw/hfi1/trace.c
浏览文件 @
8206ceb0
/*
* Copyright(c) 2015
, 2016
Intel Corporation.
* Copyright(c) 2015
- 2017
Intel Corporation.
*
* This file is provided under a dual BSD/GPLv2 license. When using or
* redistributing this file, you may do so under either license.
...
...
@@ -91,12 +91,17 @@ u8 hfi1_trace_opa_hdr_len(struct hfi1_opa_header *opa_hdr)
return
__get_16b_hdr_len
(
&
opa_hdr
->
opah
);
}
const
char
*
hfi1_trace_get_packet_
str
(
struct
hfi1_packet
*
packet
)
const
char
*
hfi1_trace_get_packet_
l4_str
(
u8
l4
)
{
if
(
packet
->
etype
!=
RHF_RCV_TYPE_BYPASS
)
return
"IB"
;
if
(
l4
)
return
"16B"
;
else
return
"9B"
;
}
switch
(
hfi1_16B_get_l2
(
packet
->
hdr
))
{
const
char
*
hfi1_trace_get_packet_l2_str
(
u8
l2
)
{
switch
(
l2
)
{
case
0
:
return
"0"
;
case
1
:
...
...
@@ -109,14 +114,6 @@ const char *hfi1_trace_get_packet_str(struct hfi1_packet *packet)
return
""
;
}
const
char
*
hfi1_trace_get_packet_type_str
(
u8
l4
)
{
if
(
l4
)
return
"16B"
;
else
return
"9B"
;
}
#define IMM_PRN "imm:%d"
#define RETH_PRN "reth vaddr:0x%.16llx rkey:0x%.8x dlen:0x%.8x"
#define AETH_PRN "aeth syn:0x%.2x %s msn:0x%.8x"
...
...
drivers/infiniband/hw/hfi1/trace.h
浏览文件 @
8206ceb0
...
...
@@ -44,6 +44,16 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
*/
#define packettype_name(etype) { RHF_RCV_TYPE_##etype, #etype }
#define show_packettype(etype) \
__print_symbolic(etype, \
packettype_name(EXPECTED), \
packettype_name(EAGER), \
packettype_name(IB), \
packettype_name(ERROR), \
packettype_name(BYPASS))
#include "trace_dbg.h"
#include "trace_misc.h"
#include "trace_ctxts.h"
...
...
drivers/infiniband/hw/hfi1/trace_ibhdrs.h
浏览文件 @
8206ceb0
/*
* Copyright(c) 2015
, 2016
Intel Corporation.
* Copyright(c) 2015
- 2017
Intel Corporation.
*
* This file is provided under a dual BSD/GPLv2 license. When using or
* redistributing this file, you may do so under either license.
...
...
@@ -99,8 +99,7 @@ u8 ibhdr_exhdr_len(struct ib_header *hdr);
const
char
*
parse_everbs_hdrs
(
struct
trace_seq
*
p
,
u8
opcode
,
void
*
ehdrs
);
u8
hfi1_trace_opa_hdr_len
(
struct
hfi1_opa_header
*
opah
);
u8
hfi1_trace_packet_hdr_len
(
struct
hfi1_packet
*
packet
);
const
char
*
hfi1_trace_get_packet_type_str
(
u8
l4
);
const
char
*
hfi1_trace_get_packet_str
(
struct
hfi1_packet
*
packet
);
const
char
*
hfi1_trace_get_packet_l4_str
(
u8
l4
);
void
hfi1_trace_parse_9b_bth
(
struct
ib_other_headers
*
ohdr
,
u8
*
ack
,
u8
*
becn
,
u8
*
fecn
,
u8
*
mig
,
u8
*
se
,
u8
*
pad
,
u8
*
opcode
,
u8
*
tver
,
...
...
@@ -129,6 +128,8 @@ const char *hfi1_trace_fmt_bth(struct trace_seq *p, bool bypass,
u8
se
,
u8
pad
,
u8
opcode
,
const
char
*
opname
,
u8
tver
,
u16
pkey
,
u32
psn
,
u32
qpn
);
const
char
*
hfi1_trace_get_packet_l2_str
(
u8
l2
);
#define __parse_ib_ehdrs(op, ehdrs) parse_everbs_hdrs(p, op, ehdrs)
#define lrh_name(lrh) { HFI1_##lrh, #lrh }
...
...
@@ -136,8 +137,6 @@ const char *hfi1_trace_fmt_bth(struct trace_seq *p, bool bypass,
__print_symbolic(lrh, \
lrh_name(LRH_BTH), \
lrh_name(LRH_GRH))
#define PKT_ENTRY(pkt) __string(ptype, hfi1_trace_get_packet_str(packet))
#define PKT_ASSIGN(pkt) __assign_str(ptype, hfi1_trace_get_packet_str(packet))
DECLARE_EVENT_CLASS
(
hfi1_input_ibhdr_template
,
TP_PROTO
(
struct
hfi1_devdata
*
dd
,
...
...
@@ -146,12 +145,12 @@ DECLARE_EVENT_CLASS(hfi1_input_ibhdr_template,
TP_ARGS
(
dd
,
packet
,
sc5
),
TP_STRUCT__entry
(
DD_DEV_ENTRY
(
dd
)
PKT_ENTRY
(
packet
)
__field
(
bool
,
bypass
)
__field
(
u8
,
etype
)
__field
(
u8
,
ack
)
__field
(
u8
,
age
)
__field
(
u8
,
becn
)
__field
(
u8
,
fecn
)
__field
(
u8
,
l2
)
__field
(
u8
,
l4
)
__field
(
u8
,
lnh
)
__field
(
u8
,
lver
)
...
...
@@ -176,10 +175,10 @@ DECLARE_EVENT_CLASS(hfi1_input_ibhdr_template,
),
TP_fast_assign
(
DD_DEV_ASSIGN
(
dd
);
PKT_ASSIGN
(
packet
);
if
(
packet
->
etype
==
RHF_RCV_TYPE_BYPASS
)
{
__entry
->
bypass
=
true
;
__entry
->
etype
=
packet
->
etype
;
__entry
->
l2
=
hfi1_16B_get_l2
(
packet
->
hdr
);
if
(
__entry
->
etype
==
RHF_RCV_TYPE_BYPASS
)
{
hfi1_trace_parse_16b_hdr
(
packet
->
hdr
,
&
__entry
->
age
,
&
__entry
->
becn
,
...
...
@@ -203,7 +202,6 @@ DECLARE_EVENT_CLASS(hfi1_input_ibhdr_template,
&
__entry
->
psn
,
&
__entry
->
qpn
);
}
else
{
__entry
->
bypass
=
false
;
hfi1_trace_parse_9b_hdr
(
packet
->
hdr
,
sc5
,
&
__entry
->
lnh
,
&
__entry
->
lver
,
...
...
@@ -233,9 +231,13 @@ DECLARE_EVENT_CLASS(hfi1_input_ibhdr_template,
),
TP_printk
(
"[%s] (%s) %s %s hlen:%d %s"
,
__get_str
(
dev
),
__get_str
(
ptype
),
__entry
->
etype
!=
RHF_RCV_TYPE_BYPASS
?
show_packettype
(
__entry
->
etype
)
:
hfi1_trace_get_packet_l2_str
(
__entry
->
l2
),
hfi1_trace_fmt_lrh
(
p
,
__entry
->
bypass
,
__entry
->
etype
==
RHF_RCV_TYPE_BYPASS
,
__entry
->
age
,
__entry
->
becn
,
__entry
->
fecn
,
...
...
@@ -252,7 +254,8 @@ DECLARE_EVENT_CLASS(hfi1_input_ibhdr_template,
__entry
->
dlid
,
__entry
->
slid
),
hfi1_trace_fmt_bth
(
p
,
__entry
->
bypass
,
__entry
->
etype
==
RHF_RCV_TYPE_BYPASS
,
__entry
->
ack
,
__entry
->
becn
,
__entry
->
fecn
,
...
...
@@ -284,7 +287,7 @@ DECLARE_EVENT_CLASS(hfi1_output_ibhdr_template,
TP_ARGS
(
dd
,
opah
,
sc5
),
TP_STRUCT__entry
(
DD_DEV_ENTRY
(
dd
)
__field
(
bool
,
bypass
)
__field
(
u8
,
hdr_type
)
__field
(
u8
,
ack
)
__field
(
u8
,
age
)
__field
(
u8
,
becn
)
...
...
@@ -316,8 +319,8 @@ DECLARE_EVENT_CLASS(hfi1_output_ibhdr_template,
DD_DEV_ASSIGN
(
dd
);
if
(
opah
->
hdr_type
)
{
__entry
->
bypass
=
true
;
__entry
->
hdr_type
=
opah
->
hdr_type
;
if
(
__entry
->
hdr_type
)
{
hfi1_trace_parse_16b_hdr
(
&
opah
->
opah
,
&
__entry
->
age
,
&
__entry
->
becn
,
...
...
@@ -345,7 +348,6 @@ DECLARE_EVENT_CLASS(hfi1_output_ibhdr_template,
&
__entry
->
psn
,
&
__entry
->
qpn
);
}
else
{
__entry
->
bypass
=
false
;
hfi1_trace_parse_9b_hdr
(
&
opah
->
ibh
,
sc5
,
&
__entry
->
lnh
,
&
__entry
->
lver
,
...
...
@@ -378,9 +380,9 @@ DECLARE_EVENT_CLASS(hfi1_output_ibhdr_template,
),
TP_printk
(
"[%s] (%s) %s %s hlen:%d %s"
,
__get_str
(
dev
),
hfi1_trace_get_packet_
type
_str
(
__entry
->
l4
),
hfi1_trace_get_packet_
l4
_str
(
__entry
->
l4
),
hfi1_trace_fmt_lrh
(
p
,
__entry
->
bypass
,
!!
__entry
->
hdr_type
,
__entry
->
age
,
__entry
->
becn
,
__entry
->
fecn
,
...
...
@@ -397,7 +399,7 @@ DECLARE_EVENT_CLASS(hfi1_output_ibhdr_template,
__entry
->
dlid
,
__entry
->
slid
),
hfi1_trace_fmt_bth
(
p
,
__entry
->
bypass
,
!!
__entry
->
hdr_type
,
__entry
->
ack
,
__entry
->
becn
,
__entry
->
fecn
,
...
...
drivers/infiniband/hw/hfi1/trace_rx.h
浏览文件 @
8206ceb0
/*
* Copyright(c) 2015
, 2016
Intel Corporation.
* Copyright(c) 2015
- 2017
Intel Corporation.
*
* This file is provided under a dual BSD/GPLv2 license. When using or
* redistributing this file, you may do so under either license.
...
...
@@ -62,15 +62,6 @@ __print_symbolic(type, \
#undef TRACE_SYSTEM
#define TRACE_SYSTEM hfi1_rx
#define packettype_name(etype) { RHF_RCV_TYPE_##etype, #etype }
#define show_packettype(etype) \
__print_symbolic(etype, \
packettype_name(EXPECTED), \
packettype_name(EAGER), \
packettype_name(IB), \
packettype_name(ERROR), \
packettype_name(BYPASS))
TRACE_EVENT
(
hfi1_rcvhdr
,
TP_PROTO
(
struct
hfi1_devdata
*
dd
,
u32
ctxt
,
...
...
drivers/infiniband/hw/hfi1/user_exp_rcv.c
浏览文件 @
8206ceb0
...
...
@@ -542,14 +542,10 @@ int hfi1_user_exp_rcv_invalid(struct hfi1_filedata *fd,
{
struct
hfi1_ctxtdata
*
uctxt
=
fd
->
uctxt
;
unsigned
long
*
ev
=
uctxt
->
dd
->
events
+
(((
uctxt
->
ctxt
-
uctxt
->
dd
->
first_dyn_alloc_ctxt
)
*
HFI1_MAX_SHARED_CTXTS
)
+
fd
->
subctxt
);
(
uctxt_offset
(
uctxt
)
+
fd
->
subctxt
);
u32
*
array
;
int
ret
=
0
;
if
(
!
fd
->
invalid_tids
)
return
-
EINVAL
;
/*
* copy_to_user() can sleep, which will leave the invalid_lock
* locked and cause the MMU notifier to be blocked on the lock
...
...
@@ -942,8 +938,7 @@ static int tid_rb_invalidate(void *arg, struct mmu_rb_node *mnode)
* process in question.
*/
ev
=
uctxt
->
dd
->
events
+
(((
uctxt
->
ctxt
-
uctxt
->
dd
->
first_dyn_alloc_ctxt
)
*
HFI1_MAX_SHARED_CTXTS
)
+
fdata
->
subctxt
);
(
uctxt_offset
(
uctxt
)
+
fdata
->
subctxt
);
set_bit
(
_HFI1_EVENT_TID_MMU_NOTIFY_BIT
,
ev
);
}
fdata
->
invalid_tid_idx
++
;
...
...
drivers/infiniband/hw/hfi1/user_sdma.c
浏览文件 @
8206ceb0
...
...
@@ -956,10 +956,8 @@ static int pin_sdma_pages(struct user_sdma_request *req,
struct
hfi1_user_sdma_pkt_q
*
pq
=
req
->
pq
;
pages
=
kcalloc
(
npages
,
sizeof
(
*
pages
),
GFP_KERNEL
);
if
(
!
pages
)
{
SDMA_DBG
(
req
,
"Failed page array alloc"
);
if
(
!
pages
)
return
-
ENOMEM
;
}
memcpy
(
pages
,
node
->
pages
,
node
->
npages
*
sizeof
(
*
pages
));
npages
-=
node
->
npages
;
...
...
@@ -1254,20 +1252,25 @@ static int set_txreq_header_ahg(struct user_sdma_request *req,
struct
user_sdma_txreq
*
tx
,
u32
datalen
)
{
u32
ahg
[
AHG_KDETH_ARRAY_SIZE
];
int
diff
=
0
;
int
idx
=
0
;
u8
omfactor
;
/* KDETH.OM */
struct
hfi1_user_sdma_pkt_q
*
pq
=
req
->
pq
;
struct
hfi1_pkt_header
*
hdr
=
&
req
->
hdr
;
u16
pbclen
=
le16_to_cpu
(
hdr
->
pbc
[
0
]);
u32
val32
,
tidval
=
0
,
lrhlen
=
get_lrh_len
(
*
hdr
,
pad_len
(
datalen
));
size_t
array_size
=
ARRAY_SIZE
(
ahg
);
if
(
PBC2LRH
(
pbclen
)
!=
lrhlen
)
{
/* PBC.PbcLengthDWs */
AHG_HEADER_SET
(
ahg
,
diff
,
0
,
0
,
12
,
cpu_to_le16
(
LRH2PBC
(
lrhlen
)));
idx
=
ahg_header_set
(
ahg
,
idx
,
array_size
,
0
,
0
,
12
,
(
__force
u16
)
cpu_to_le16
(
LRH2PBC
(
lrhlen
)));
if
(
idx
<
0
)
return
idx
;
/* LRH.PktLen (we need the full 16 bits due to byte swap) */
AHG_HEADER_SET
(
ahg
,
diff
,
3
,
0
,
16
,
cpu_to_be16
(
lrhlen
>>
2
));
idx
=
ahg_header_set
(
ahg
,
idx
,
array_size
,
3
,
0
,
16
,
(
__force
u16
)
cpu_to_be16
(
lrhlen
>>
2
));
if
(
idx
<
0
)
return
idx
;
}
/*
...
...
@@ -1278,12 +1281,23 @@ static int set_txreq_header_ahg(struct user_sdma_request *req,
(
HFI1_CAP_IS_KSET
(
EXTENDED_PSN
)
?
0x7fffffff
:
0xffffff
);
if
(
unlikely
(
tx
->
flags
&
TXREQ_FLAGS_REQ_ACK
))
val32
|=
1UL
<<
31
;
AHG_HEADER_SET
(
ahg
,
diff
,
6
,
0
,
16
,
cpu_to_be16
(
val32
>>
16
));
AHG_HEADER_SET
(
ahg
,
diff
,
6
,
16
,
16
,
cpu_to_be16
(
val32
&
0xffff
));
idx
=
ahg_header_set
(
ahg
,
idx
,
array_size
,
6
,
0
,
16
,
(
__force
u16
)
cpu_to_be16
(
val32
>>
16
));
if
(
idx
<
0
)
return
idx
;
idx
=
ahg_header_set
(
ahg
,
idx
,
array_size
,
6
,
16
,
16
,
(
__force
u16
)
cpu_to_be16
(
val32
&
0xffff
));
if
(
idx
<
0
)
return
idx
;
/* KDETH.Offset */
AHG_HEADER_SET
(
ahg
,
diff
,
15
,
0
,
16
,
cpu_to_le16
(
req
->
koffset
&
0xffff
));
AHG_HEADER_SET
(
ahg
,
diff
,
15
,
16
,
16
,
cpu_to_le16
(
req
->
koffset
>>
16
));
idx
=
ahg_header_set
(
ahg
,
idx
,
array_size
,
15
,
0
,
16
,
(
__force
u16
)
cpu_to_le16
(
req
->
koffset
&
0xffff
));
if
(
idx
<
0
)
return
idx
;
idx
=
ahg_header_set
(
ahg
,
idx
,
array_size
,
15
,
16
,
16
,
(
__force
u16
)
cpu_to_le16
(
req
->
koffset
>>
16
));
if
(
idx
<
0
)
return
idx
;
if
(
req_opcode
(
req
->
info
.
ctrl
)
==
EXPECTED
)
{
__le16
val
;
...
...
@@ -1310,10 +1324,13 @@ static int set_txreq_header_ahg(struct user_sdma_request *req,
KDETH_OM_MAX_SIZE
)
?
KDETH_OM_LARGE_SHIFT
:
KDETH_OM_SMALL_SHIFT
;
/* KDETH.OM and KDETH.OFFSET (TID) */
AHG_HEADER_SET
(
ahg
,
diff
,
7
,
0
,
16
,
((
!!
(
omfactor
-
KDETH_OM_SMALL_SHIFT
))
<<
15
|
idx
=
ahg_header_set
(
ahg
,
idx
,
array_size
,
7
,
0
,
16
,
((
!!
(
omfactor
-
KDETH_OM_SMALL_SHIFT
))
<<
15
|
((
req
->
tidoffset
>>
omfactor
)
&
0x7fff
)));
&
0x7fff
)));
if
(
idx
<
0
)
return
idx
;
/* KDETH.TIDCtrl, KDETH.TID, KDETH.Intr, KDETH.SH */
val
=
cpu_to_le16
(((
EXP_TID_GET
(
tidval
,
CTRL
)
&
0x3
)
<<
10
)
|
(
EXP_TID_GET
(
tidval
,
IDX
)
&
0x3ff
));
...
...
@@ -1330,21 +1347,22 @@ static int set_txreq_header_ahg(struct user_sdma_request *req,
AHG_KDETH_INTR_SHIFT
));
}
AHG_HEADER_SET
(
ahg
,
diff
,
7
,
16
,
14
,
val
);
idx
=
ahg_header_set
(
ahg
,
idx
,
array_size
,
7
,
16
,
14
,
(
__force
u16
)
val
);
if
(
idx
<
0
)
return
idx
;
}
if
(
diff
<
0
)
return
diff
;
trace_hfi1_sdma_user_header_ahg
(
pq
->
dd
,
pq
->
ctxt
,
pq
->
subctxt
,
req
->
info
.
comp_idx
,
req
->
sde
->
this_idx
,
req
->
ahg_idx
,
ahg
,
diff
,
tidval
);
req
->
ahg_idx
,
ahg
,
idx
,
tidval
);
sdma_txinit_ahg
(
&
tx
->
txreq
,
SDMA_TXREQ_F_USE_AHG
,
datalen
,
req
->
ahg_idx
,
diff
,
datalen
,
req
->
ahg_idx
,
idx
,
ahg
,
sizeof
(
req
->
hdr
),
user_sdma_txreq_cb
);
return
diff
;
return
idx
;
}
/*
...
...
drivers/infiniband/hw/hfi1/user_sdma.h
浏览文件 @
8206ceb0
...
...
@@ -80,15 +80,26 @@
#define PBC2LRH(x) ((((x) & 0xfff) << 2) - 4)
#define LRH2PBC(x) ((((x) >> 2) + 1) & 0xfff)
#define AHG_HEADER_SET(arr, idx, dw, bit, width, value) \
do { \
if ((idx) < ARRAY_SIZE((arr))) \
(arr)[(idx++)] = sdma_build_ahg_descriptor( \
(__force u16)(value), (dw), (bit), \
(width)); \
else \
return -ERANGE; \
} while (0)
/**
* Build an SDMA AHG header update descriptor and save it to an array.
* @arr - Array to save the descriptor to.
* @idx - Index of the array at which the descriptor will be saved.
* @array_size - Size of the array arr.
* @dw - Update index into the header in DWs.
* @bit - Start bit.
* @width - Field width.
* @value - 16 bits of immediate data to write into the field.
* Returns -ERANGE if idx is invalid. If successful, returns the next index
* (idx + 1) of the array to be used for the next descriptor.
*/
static
inline
int
ahg_header_set
(
u32
*
arr
,
int
idx
,
size_t
array_size
,
u8
dw
,
u8
bit
,
u8
width
,
u16
value
)
{
if
((
size_t
)
idx
>=
array_size
)
return
-
ERANGE
;
arr
[
idx
++
]
=
sdma_build_ahg_descriptor
(
value
,
dw
,
bit
,
width
);
return
idx
;
}
/* Tx request flag bits */
#define TXREQ_FLAGS_REQ_ACK BIT(0)
/* Set the ACK bit in the header */
...
...
drivers/infiniband/hw/qib/qib.h
浏览文件 @
8206ceb0
...
...
@@ -443,14 +443,12 @@ struct qib_irq_notify;
#endif
struct
qib_msix_entry
{
int
irq
;
void
*
arg
;
#ifdef CONFIG_INFINIBAND_QIB_DCA
int
dca
;
int
rcv
;
struct
qib_irq_notify
*
notifier
;
#endif
char
name
[
MAX_NAME_SIZE
];
cpumask_var_t
mask
;
};
...
...
@@ -1434,10 +1432,8 @@ int qib_pcie_ddinit(struct qib_devdata *, struct pci_dev *,
const
struct
pci_device_id
*
);
void
qib_pcie_ddcleanup
(
struct
qib_devdata
*
);
int
qib_pcie_params
(
struct
qib_devdata
*
dd
,
u32
minw
,
u32
*
nent
);
int
qib_reinit_intr
(
struct
qib_devdata
*
);
void
qib_enable_intx
(
struct
qib_devdata
*
dd
);
void
qib_nomsi
(
struct
qib_devdata
*
);
void
qib_nomsix
(
struct
qib_devdata
*
);
void
qib_free_irq
(
struct
qib_devdata
*
dd
);
int
qib_reinit_intr
(
struct
qib_devdata
*
dd
);
void
qib_pcie_getcmd
(
struct
qib_devdata
*
,
u16
*
,
u8
*
,
u8
*
);
void
qib_pcie_reenable
(
struct
qib_devdata
*
,
u16
,
u8
,
u8
);
/* interrupts for device */
...
...
drivers/infiniband/hw/qib/qib_7220.h
浏览文件 @
8206ceb0
...
...
@@ -67,7 +67,6 @@ struct qib_chip_specific {
u32
lastbuf_for_pio
;
u32
updthresh
;
/* current AvailUpdThld */
u32
updthresh_dflt
;
/* default AvailUpdThld */
int
irq
;
u8
presets_needed
;
u8
relock_timer_active
;
char
emsgbuf
[
128
];
...
...
drivers/infiniband/hw/qib/qib_iba6120.c
浏览文件 @
8206ceb0
...
...
@@ -245,7 +245,6 @@ struct qib_chip_specific {
u64
iblnkerrsnap
;
u64
ibcctrl
;
/* shadow for kr_ibcctrl */
u32
lastlinkrecov
;
/* link recovery issue */
int
irq
;
u32
cntrnamelen
;
u32
portcntrnamelen
;
u32
ncntrs
;
...
...
@@ -1485,15 +1484,6 @@ static void qib_6120_setup_setextled(struct qib_pportdata *ppd, u32 on)
spin_unlock_irqrestore
(
&
dd
->
cspec
->
gpio_lock
,
flags
);
}
static
void
qib_6120_free_irq
(
struct
qib_devdata
*
dd
)
{
if
(
dd
->
cspec
->
irq
)
{
free_irq
(
dd
->
cspec
->
irq
,
dd
);
dd
->
cspec
->
irq
=
0
;
}
qib_nomsi
(
dd
);
}
/**
* qib_6120_setup_cleanup - clean up any per-chip chip-specific stuff
* @dd: the qlogic_ib device
...
...
@@ -1502,7 +1492,7 @@ static void qib_6120_free_irq(struct qib_devdata *dd)
*/
static
void
qib_6120_setup_cleanup
(
struct
qib_devdata
*
dd
)
{
qib_
6120_
free_irq
(
dd
);
qib_free_irq
(
dd
);
kfree
(
dd
->
cspec
->
cntrs
);
kfree
(
dd
->
cspec
->
portcntrs
);
if
(
dd
->
cspec
->
dummy_hdrq
)
{
...
...
@@ -1706,6 +1696,8 @@ static irqreturn_t qib_6120intr(int irq, void *data)
*/
static
void
qib_setup_6120_interrupt
(
struct
qib_devdata
*
dd
)
{
int
ret
;
/*
* If the chip supports added error indication via GPIO pins,
* enable interrupts on those bits so the interrupt routine
...
...
@@ -1719,19 +1711,12 @@ static void qib_setup_6120_interrupt(struct qib_devdata *dd)
qib_write_kreg
(
dd
,
kr_gpio_mask
,
dd
->
cspec
->
gpio_mask
);
}
if
(
!
dd
->
cspec
->
irq
)
ret
=
pci_request_irq
(
dd
->
pcidev
,
0
,
qib_6120intr
,
NULL
,
dd
,
QIB_DRV_NAME
);
if
(
ret
)
qib_dev_err
(
dd
,
"irq is 0, BIOS error? Interrupts won't work
\n
"
);
else
{
int
ret
;
ret
=
request_irq
(
dd
->
cspec
->
irq
,
qib_6120intr
,
0
,
QIB_DRV_NAME
,
dd
);
if
(
ret
)
qib_dev_err
(
dd
,
"Couldn't setup interrupt (irq=%d): %d
\n
"
,
dd
->
cspec
->
irq
,
ret
);
}
"Couldn't setup interrupt (irq=%d): %d
\n
"
,
pci_irq_vector
(
dd
->
pcidev
,
0
),
ret
);
}
/**
...
...
@@ -3490,7 +3475,7 @@ struct qib_devdata *qib_init_iba6120_funcs(struct pci_dev *pdev,
dd
->
f_bringup_serdes
=
qib_6120_bringup_serdes
;
dd
->
f_cleanup
=
qib_6120_setup_cleanup
;
dd
->
f_clear_tids
=
qib_6120_clear_tids
;
dd
->
f_free_irq
=
qib_
6120_
free_irq
;
dd
->
f_free_irq
=
qib_free_irq
;
dd
->
f_get_base_info
=
qib_6120_get_base_info
;
dd
->
f_get_msgheader
=
qib_6120_get_msgheader
;
dd
->
f_getsendbuf
=
qib_6120_getsendbuf
;
...
...
@@ -3559,8 +3544,6 @@ struct qib_devdata *qib_init_iba6120_funcs(struct pci_dev *pdev,
if
(
qib_pcie_params
(
dd
,
8
,
NULL
))
qib_dev_err
(
dd
,
"Failed to setup PCIe or interrupts; continuing anyway
\n
"
);
dd
->
cspec
->
irq
=
pdev
->
irq
;
/* save IRQ */
/* clear diagctrl register, in case diags were running and crashed */
qib_write_kreg
(
dd
,
kr_hwdiagctrl
,
0
);
...
...
drivers/infiniband/hw/qib/qib_iba7220.c
浏览文件 @
8206ceb0
...
...
@@ -1780,15 +1780,6 @@ static void qib_setup_7220_setextled(struct qib_pportdata *ppd, u32 on)
qib_write_kreg
(
dd
,
kr_rcvpktledcnt
,
ledblink
);
}
static
void
qib_7220_free_irq
(
struct
qib_devdata
*
dd
)
{
if
(
dd
->
cspec
->
irq
)
{
free_irq
(
dd
->
cspec
->
irq
,
dd
);
dd
->
cspec
->
irq
=
0
;
}
qib_nomsi
(
dd
);
}
/*
* qib_setup_7220_cleanup - clean up any per-chip chip-specific stuff
* @dd: the qlogic_ib device
...
...
@@ -1798,7 +1789,7 @@ static void qib_7220_free_irq(struct qib_devdata *dd)
*/
static
void
qib_setup_7220_cleanup
(
struct
qib_devdata
*
dd
)
{
qib_
7220_
free_irq
(
dd
);
qib_free_irq
(
dd
);
kfree
(
dd
->
cspec
->
cntrs
);
kfree
(
dd
->
cspec
->
portcntrs
);
}
...
...
@@ -2026,20 +2017,14 @@ static irqreturn_t qib_7220intr(int irq, void *data)
*/
static
void
qib_setup_7220_interrupt
(
struct
qib_devdata
*
dd
)
{
if
(
!
dd
->
cspec
->
irq
)
qib_dev_err
(
dd
,
"irq is 0, BIOS error? Interrupts won't work
\n
"
);
else
{
int
ret
=
request_irq
(
dd
->
cspec
->
irq
,
qib_7220intr
,
dd
->
msi_lo
?
0
:
IRQF_SHARED
,
QIB_DRV_NAME
,
dd
);
int
ret
;
if
(
ret
)
qib_dev_err
(
dd
,
"Couldn't setup %s interrupt (irq=%d): %d
\n
"
,
dd
->
msi_lo
?
"MSI"
:
"INTx
"
,
dd
->
cspec
->
irq
,
ret
);
}
ret
=
pci_request_irq
(
dd
->
pcidev
,
0
,
qib_7220intr
,
NULL
,
dd
,
QIB_DRV_NAME
);
if
(
ret
)
qib_dev_err
(
dd
,
"Couldn't setup %s interrupt (irq=%d): %d
\n
"
,
dd
->
pcidev
->
msi_enabled
?
"MSI"
:
"INTx"
,
pci_irq_vector
(
dd
->
pcidev
,
0
),
ret
);
}
/**
...
...
@@ -3302,16 +3287,12 @@ static int qib_7220_intr_fallback(struct qib_devdata *dd)
return
0
;
qib_devinfo
(
dd
->
pcidev
,
"MSI interrupt not detected, trying INTx interrupts
\n
"
);
qib_7220_free_irq
(
dd
);
qib_enable_intx
(
dd
);
/*
* Some newer kernels require free_irq before disable_msi,
* and irq can be changed during disable and INTx enable
* and we need to therefore use the pcidev->irq value,
* not our saved MSI value.
*/
dd
->
cspec
->
irq
=
dd
->
pcidev
->
irq
;
"MSI interrupt not detected, trying INTx interrupts
\n
"
);
qib_free_irq
(
dd
);
dd
->
msi_lo
=
0
;
if
(
pci_alloc_irq_vectors
(
dd
->
pcidev
,
1
,
1
,
PCI_IRQ_LEGACY
)
<
0
)
qib_dev_err
(
dd
,
"Failed to enable INTx
\n
"
);
qib_setup_7220_interrupt
(
dd
);
return
1
;
}
...
...
@@ -4535,7 +4516,7 @@ struct qib_devdata *qib_init_iba7220_funcs(struct pci_dev *pdev,
dd
->
f_bringup_serdes
=
qib_7220_bringup_serdes
;
dd
->
f_cleanup
=
qib_setup_7220_cleanup
;
dd
->
f_clear_tids
=
qib_7220_clear_tids
;
dd
->
f_free_irq
=
qib_
7220_
free_irq
;
dd
->
f_free_irq
=
qib_free_irq
;
dd
->
f_get_base_info
=
qib_7220_get_base_info
;
dd
->
f_get_msgheader
=
qib_7220_get_msgheader
;
dd
->
f_getsendbuf
=
qib_7220_getsendbuf
;
...
...
@@ -4618,9 +4599,6 @@ struct qib_devdata *qib_init_iba7220_funcs(struct pci_dev *pdev,
qib_dev_err
(
dd
,
"Failed to setup PCIe or interrupts; continuing anyway
\n
"
);
/* save IRQ for possible later use */
dd
->
cspec
->
irq
=
pdev
->
irq
;
if
(
qib_read_kreg64
(
dd
,
kr_hwerrstatus
)
&
QLOGIC_IB_HWE_SERDESPLLFAILED
)
qib_write_kreg
(
dd
,
kr_hwerrclear
,
...
...
drivers/infiniband/hw/qib/qib_iba7322.c
浏览文件 @
8206ceb0
...
...
@@ -553,7 +553,6 @@ struct qib_chip_specific {
u32
updthresh
;
/* current AvailUpdThld */
u32
updthresh_dflt
;
/* default AvailUpdThld */
u32
r1
;
int
irq
;
u32
num_msix_entries
;
u32
sdmabufcnt
;
u32
lastbuf_for_pio
;
...
...
@@ -756,10 +755,8 @@ static void check_7322_rxe_status(struct qib_pportdata *);
static
u32
__iomem
*
qib_7322_getsendbuf
(
struct
qib_pportdata
*
,
u64
,
u32
*
);
#ifdef CONFIG_INFINIBAND_QIB_DCA
static
void
qib_setup_dca
(
struct
qib_devdata
*
dd
);
static
void
setup_dca_notifier
(
struct
qib_devdata
*
dd
,
struct
qib_msix_entry
*
m
);
static
void
reset_dca_notifier
(
struct
qib_devdata
*
dd
,
struct
qib_msix_entry
*
m
);
static
void
setup_dca_notifier
(
struct
qib_devdata
*
dd
,
int
msixnum
);
static
void
reset_dca_notifier
(
struct
qib_devdata
*
dd
,
int
msixnum
);
#endif
/**
...
...
@@ -2778,7 +2775,7 @@ static void qib_setup_dca(struct qib_devdata *dd)
qib_write_kreg
(
dd
,
KREG_IDX
(
DCACtrlB
)
+
i
,
cspec
->
dca_rcvhdr_ctrl
[
i
]);
for
(
i
=
0
;
i
<
cspec
->
num_msix_entries
;
i
++
)
setup_dca_notifier
(
dd
,
&
cspec
->
msix_entries
[
i
]
);
setup_dca_notifier
(
dd
,
i
);
}
static
void
qib_irq_notifier_notify
(
struct
irq_affinity_notify
*
notify
,
...
...
@@ -2820,49 +2817,41 @@ static void qib_irq_notifier_release(struct kref *ref)
}
#endif
/*
* Disable MSIx interrupt if enabled, call generic MSIx code
* to cleanup, and clear pending MSIx interrupts.
* Used for fallback to INTx, after reset, and when MSIx setup fails.
*/
static
void
qib_7322_nomsix
(
struct
qib_devdata
*
dd
)
static
void
qib_7322_free_irq
(
struct
qib_devdata
*
dd
)
{
u64
intgranted
;
int
n
;
int
i
;
dd
->
cspec
->
main_int_mask
=
~
0ULL
;
n
=
dd
->
cspec
->
num_msix_entries
;
if
(
n
)
{
int
i
;
dd
->
cspec
->
num_msix_entries
=
0
;
for
(
i
=
0
;
i
<
n
;
i
++
)
{
for
(
i
=
0
;
i
<
dd
->
cspec
->
num_msix_entries
;
i
++
)
{
/* only free IRQs that were allocated */
if
(
dd
->
cspec
->
msix_entries
[
i
].
arg
)
{
#ifdef CONFIG_INFINIBAND_QIB_DCA
reset_dca_notifier
(
dd
,
&
dd
->
cspec
->
msix_entries
[
i
]
);
reset_dca_notifier
(
dd
,
i
);
#endif
irq_set_affinity_hint
(
dd
->
cspec
->
msix_entries
[
i
].
irq
,
NULL
);
irq_set_affinity_hint
(
pci_irq_vector
(
dd
->
pcidev
,
i
),
NULL
);
free_cpumask_var
(
dd
->
cspec
->
msix_entries
[
i
].
mask
);
free_irq
(
dd
->
cspec
->
msix_entries
[
i
].
irq
,
dd
->
cspec
->
msix_entries
[
i
].
arg
);
pci_free_irq
(
dd
->
pcidev
,
i
,
dd
->
cspec
->
msix_entries
[
i
].
arg
);
}
qib_nomsix
(
dd
);
}
/* If num_msix_entries was 0, disable the INTx IRQ */
if
(
!
dd
->
cspec
->
num_msix_entries
)
pci_free_irq
(
dd
->
pcidev
,
0
,
dd
);
else
dd
->
cspec
->
num_msix_entries
=
0
;
pci_free_irq_vectors
(
dd
->
pcidev
);
/* make sure no MSIx interrupts are left pending */
intgranted
=
qib_read_kreg64
(
dd
,
kr_intgranted
);
if
(
intgranted
)
qib_write_kreg
(
dd
,
kr_intgranted
,
intgranted
);
}
static
void
qib_7322_free_irq
(
struct
qib_devdata
*
dd
)
{
if
(
dd
->
cspec
->
irq
)
{
free_irq
(
dd
->
cspec
->
irq
,
dd
);
dd
->
cspec
->
irq
=
0
;
}
qib_7322_nomsix
(
dd
);
}
static
void
qib_setup_7322_cleanup
(
struct
qib_devdata
*
dd
)
{
int
i
;
...
...
@@ -3329,22 +3318,20 @@ static irqreturn_t sdma_cleanup_intr(int irq, void *data)
#ifdef CONFIG_INFINIBAND_QIB_DCA
static
void
reset_dca_notifier
(
struct
qib_devdata
*
dd
,
struct
qib_msix_entry
*
m
)
static
void
reset_dca_notifier
(
struct
qib_devdata
*
dd
,
int
msixnu
m
)
{
if
(
!
m
->
dca
)
if
(
!
dd
->
cspec
->
msix_entries
[
msixnum
].
dca
)
return
;
qib_devinfo
(
dd
->
pcidev
,
"Disabling notifier on HCA %d irq %d
\n
"
,
dd
->
unit
,
m
->
irq
);
irq_set_affinity_notifier
(
m
->
irq
,
NULL
);
m
->
notifier
=
NULL
;
qib_devinfo
(
dd
->
pcidev
,
"Disabling notifier on HCA %d irq %d
\n
"
,
dd
->
unit
,
pci_irq_vector
(
dd
->
pcidev
,
msixnum
));
irq_set_affinity_notifier
(
pci_irq_vector
(
dd
->
pcidev
,
msixnum
),
NULL
);
dd
->
cspec
->
msix_entries
[
msixnum
].
notifier
=
NULL
;
}
static
void
setup_dca_notifier
(
struct
qib_devdata
*
dd
,
struct
qib_msix_entry
*
m
)
static
void
setup_dca_notifier
(
struct
qib_devdata
*
dd
,
int
msixnu
m
)
{
struct
qib_msix_entry
*
m
=
&
dd
->
cspec
->
msix_entries
[
msixnum
];
struct
qib_irq_notify
*
n
;
if
(
!
m
->
dca
)
...
...
@@ -3354,7 +3341,7 @@ static void setup_dca_notifier(struct qib_devdata *dd, struct qib_msix_entry *m)
int
ret
;
m
->
notifier
=
n
;
n
->
notify
.
irq
=
m
->
irq
;
n
->
notify
.
irq
=
pci_irq_vector
(
dd
->
pcidev
,
msixnum
)
;
n
->
notify
.
notify
=
qib_irq_notifier_notify
;
n
->
notify
.
release
=
qib_irq_notifier_release
;
n
->
arg
=
m
->
arg
;
...
...
@@ -3415,22 +3402,17 @@ static void qib_setup_7322_interrupt(struct qib_devdata *dd, int clearpend)
if
(
!
dd
->
cspec
->
num_msix_entries
)
{
/* Try to get INTx interrupt */
try_intx:
if
(
!
dd
->
pcidev
->
irq
)
{
qib_dev_err
(
dd
,
"irq is 0, BIOS error? Interrupts won't work
\n
"
);
goto
bail
;
}
ret
=
request_irq
(
dd
->
pcidev
->
irq
,
qib_7322intr
,
IRQF_SHARED
,
QIB_DRV_NAME
,
dd
);
ret
=
pci_request_irq
(
dd
->
pcidev
,
0
,
qib_7322intr
,
NULL
,
dd
,
QIB_DRV_NAME
);
if
(
ret
)
{
qib_dev_err
(
dd
,
qib_dev_err
(
dd
,
"Couldn't setup INTx interrupt (irq=%d): %d
\n
"
,
dd
->
pcidev
->
irq
,
ret
);
goto
bail
;
pci_irq_vector
(
dd
->
pcidev
,
0
)
,
ret
);
return
;
}
dd
->
cspec
->
irq
=
dd
->
pcidev
->
irq
;
dd
->
cspec
->
main_int_mask
=
~
0ULL
;
goto
bail
;
return
;
}
/* Try to get MSIx interrupts */
...
...
@@ -3458,10 +3440,6 @@ static void qib_setup_7322_interrupt(struct qib_devdata *dd, int clearpend)
#ifdef CONFIG_INFINIBAND_QIB_DCA
int
dca
=
0
;
#endif
dd
->
cspec
->
msix_entries
[
msixnum
].
name
[
sizeof
(
dd
->
cspec
->
msix_entries
[
msixnum
].
name
)
-
1
]
=
'\0'
;
if
(
i
<
ARRAY_SIZE
(
irq_table
))
{
if
(
irq_table
[
i
].
port
)
{
/* skip if for a non-configured port */
...
...
@@ -3475,11 +3453,10 @@ static void qib_setup_7322_interrupt(struct qib_devdata *dd, int clearpend)
#endif
lsb
=
irq_table
[
i
].
lsb
;
handler
=
irq_table
[
i
].
handler
;
snprintf
(
dd
->
cspec
->
msix_entries
[
msixnum
].
name
,
sizeof
(
dd
->
cspec
->
msix_entries
[
msixnum
].
name
)
-
1
,
QIB_DRV_NAME
"%d%s"
,
dd
->
unit
,
irq_table
[
i
].
name
);
ret
=
pci_request_irq
(
dd
->
pcidev
,
msixnum
,
handler
,
NULL
,
arg
,
QIB_DRV_NAME
"%d%s"
,
dd
->
unit
,
irq_table
[
i
].
name
);
}
else
{
unsigned
ctxt
;
...
...
@@ -3495,37 +3472,25 @@ static void qib_setup_7322_interrupt(struct qib_devdata *dd, int clearpend)
#endif
lsb
=
QIB_I_RCVAVAIL_LSB
+
ctxt
;
handler
=
qib_7322pintr
;
snprintf
(
dd
->
cspec
->
msix_entries
[
msixnum
].
name
,
sizeof
(
dd
->
cspec
->
msix_entries
[
msixnum
].
name
)
-
1
,
QIB_DRV_NAME
"%d (kctx)"
,
dd
->
unit
);
ret
=
pci_request_irq
(
dd
->
pcidev
,
msixnum
,
handler
,
NULL
,
arg
,
QIB_DRV_NAME
"%d (kctx)"
,
dd
->
unit
);
}
dd
->
cspec
->
msix_entries
[
msixnum
].
irq
=
pci_irq_vector
(
dd
->
pcidev
,
msixnum
);
if
(
dd
->
cspec
->
msix_entries
[
msixnum
].
irq
<
0
)
{
qib_dev_err
(
dd
,
"Couldn't get MSIx irq (vec=%d): %d
\n
"
,
msixnum
,
dd
->
cspec
->
msix_entries
[
msixnum
].
irq
);
qib_7322_nomsix
(
dd
);
goto
try_intx
;
}
ret
=
request_irq
(
dd
->
cspec
->
msix_entries
[
msixnum
].
irq
,
handler
,
0
,
dd
->
cspec
->
msix_entries
[
msixnum
].
name
,
arg
);
if
(
ret
)
{
/*
* Shouldn't happen since the enable said we could
* have as many as we are trying to setup here.
*/
qib_dev_err
(
dd
,
"Couldn't setup MSIx interrupt (vec=%d, irq=%d): %d
\n
"
,
msixnum
,
dd
->
cspec
->
msix_entries
[
msixnum
].
irq
,
ret
);
qib_7322_nomsix
(
dd
);
"Couldn't setup MSIx interrupt (vec=%d, irq=%d): %d
\n
"
,
msixnum
,
pci_irq_vector
(
dd
->
pcidev
,
msixnum
),
ret
);
qib_7322_free_irq
(
dd
);
pci_alloc_irq_vectors
(
dd
->
pcidev
,
1
,
1
,
PCI_IRQ_LEGACY
);
goto
try_intx
;
}
dd
->
cspec
->
msix_entries
[
msixnum
].
arg
=
arg
;
...
...
@@ -3559,7 +3524,7 @@ static void qib_setup_7322_interrupt(struct qib_devdata *dd, int clearpend)
dd
->
cspec
->
msix_entries
[
msixnum
].
mask
);
}
irq_set_affinity_hint
(
dd
->
cspec
->
msix_entries
[
msixnum
].
irq
,
pci_irq_vector
(
dd
->
pcidev
,
msixnum
)
,
dd
->
cspec
->
msix_entries
[
msixnum
].
mask
);
}
msixnum
++
;
...
...
@@ -3570,7 +3535,6 @@ static void qib_setup_7322_interrupt(struct qib_devdata *dd, int clearpend)
dd
->
cspec
->
main_int_mask
=
mask
;
tasklet_init
(
&
dd
->
error_tasklet
,
qib_error_tasklet
,
(
unsigned
long
)
dd
);
bail:
;
}
/**
...
...
@@ -3674,8 +3638,9 @@ static int qib_do_7322_reset(struct qib_devdata *dd)
/* no interrupts till re-initted */
qib_7322_set_intr_state
(
dd
,
0
);
qib_7322_free_irq
(
dd
);
if
(
msix_entries
)
{
qib_7322_nomsix
(
dd
);
/* can be up to 512 bytes, too big for stack */
msix_vecsave
=
kmalloc
(
2
*
dd
->
cspec
->
num_msix_entries
*
sizeof
(
u64
),
GFP_KERNEL
);
...
...
@@ -3765,11 +3730,11 @@ static int qib_do_7322_reset(struct qib_devdata *dd)
write_7322_init_portregs
(
&
dd
->
pport
[
i
]);
write_7322_initregs
(
dd
);
if
(
qib_pcie_params
(
dd
,
dd
->
lbus_width
,
&
dd
->
cspec
->
num_msix_entries
))
if
(
qib_pcie_params
(
dd
,
dd
->
lbus_width
,
&
msix_entries
))
qib_dev_err
(
dd
,
"Reset failed to setup PCIe or interrupts; continuing anyway
\n
"
);
dd
->
cspec
->
num_msix_entries
=
msix_entries
;
qib_setup_7322_interrupt
(
dd
,
1
);
for
(
i
=
0
;
i
<
dd
->
num_pports
;
++
i
)
{
...
...
@@ -5197,8 +5162,9 @@ static int qib_7322_intr_fallback(struct qib_devdata *dd)
qib_devinfo
(
dd
->
pcidev
,
"MSIx interrupt not detected, trying INTx interrupts
\n
"
);
qib_7322_nomsix
(
dd
);
qib_enable_intx
(
dd
);
qib_7322_free_irq
(
dd
);
if
(
pci_alloc_irq_vectors
(
dd
->
pcidev
,
1
,
1
,
PCI_IRQ_LEGACY
)
<
0
)
qib_dev_err
(
dd
,
"Failed to enable INTx
\n
"
);
qib_setup_7322_interrupt
(
dd
,
0
);
return
1
;
}
...
...
drivers/infiniband/hw/qib/qib_pcie.c
浏览文件 @
8206ceb0
...
...
@@ -193,7 +193,7 @@ void qib_pcie_ddcleanup(struct qib_devdata *dd)
* chip reset (the kernel PCI infrastructure doesn't yet handle that
* correctly.
*/
static
void
qib_
msi_setup
(
struct
qib_devdata
*
dd
,
int
pos
)
static
void
qib_
cache_msi_info
(
struct
qib_devdata
*
dd
,
int
pos
)
{
struct
pci_dev
*
pdev
=
dd
->
pcidev
;
u16
control
;
...
...
@@ -208,64 +208,39 @@ static void qib_msi_setup(struct qib_devdata *dd, int pos)
&
dd
->
msi_data
);
}
static
int
qib_allocate_irqs
(
struct
qib_devdata
*
dd
,
u32
maxvec
)
{
unsigned
int
flags
=
PCI_IRQ_LEGACY
;
/* Check our capabilities */
if
(
dd
->
pcidev
->
msix_cap
)
{
flags
|=
PCI_IRQ_MSIX
;
}
else
{
if
(
dd
->
pcidev
->
msi_cap
)
{
flags
|=
PCI_IRQ_MSI
;
/* Get msi_lo and msi_hi */
qib_msi_setup
(
dd
,
dd
->
pcidev
->
msi_cap
);
}
}
if
(
!
(
flags
&
(
PCI_IRQ_MSIX
|
PCI_IRQ_MSI
)))
qib_dev_err
(
dd
,
"No PCI MSI or MSIx capability!
\n
"
);
return
pci_alloc_irq_vectors
(
dd
->
pcidev
,
1
,
maxvec
,
flags
);
}
int
qib_pcie_params
(
struct
qib_devdata
*
dd
,
u32
minw
,
u32
*
nent
)
{
u16
linkstat
,
speed
;
int
nvec
;
int
maxvec
;
int
ret
=
0
;
unsigned
int
flags
=
PCI_IRQ_MSIX
|
PCI_IRQ_MSI
;
if
(
!
pci_is_pcie
(
dd
->
pcidev
))
{
qib_dev_err
(
dd
,
"Can't find PCI Express capability!
\n
"
);
/* set up something... */
dd
->
lbus_width
=
1
;
dd
->
lbus_speed
=
2500
;
/* Gen1, 2.5GHz */
ret
=
-
1
;
nvec
=
-
1
;
goto
bail
;
}
if
(
dd
->
flags
&
QIB_HAS_INTX
)
flags
|=
PCI_IRQ_LEGACY
;
maxvec
=
(
nent
&&
*
nent
)
?
*
nent
:
1
;
nvec
=
qib_allocate_irqs
(
dd
,
maxvec
);
if
(
nvec
<
0
)
{
ret
=
nvec
;
nvec
=
pci_alloc_irq_vectors
(
dd
->
pcidev
,
1
,
maxvec
,
flags
);
if
(
nvec
<
0
)
goto
bail
;
}
/*
* If nent exists, make sure to record how many vectors were allocated
* If nent exists, make sure to record how many vectors were allocated.
* If msix_enabled is false, return 0 so the fallback code works
* correctly.
*/
if
(
nent
)
{
*
nent
=
nvec
;
if
(
nent
)
*
nent
=
!
dd
->
pcidev
->
msix_enabled
?
0
:
nvec
;
/*
* If we requested (nent) MSIX, but msix_enabled is not set,
* pci_alloc_irq_vectors() enabled INTx.
*/
if
(
!
dd
->
pcidev
->
msix_enabled
)
qib_dev_err
(
dd
,
"no msix vectors allocated, using INTx
\n
"
);
}
if
(
dd
->
pcidev
->
msi_enabled
)
qib_cache_msi_info
(
dd
,
dd
->
pcidev
->
msi_cap
);
pcie_capability_read_word
(
dd
->
pcidev
,
PCI_EXP_LNKSTA
,
&
linkstat
);
/*
...
...
@@ -306,7 +281,21 @@ int qib_pcie_params(struct qib_devdata *dd, u32 minw, u32 *nent)
/* fill in string, even on errors */
snprintf
(
dd
->
lbus_info
,
sizeof
(
dd
->
lbus_info
),
"PCIe,%uMHz,x%u
\n
"
,
dd
->
lbus_speed
,
dd
->
lbus_width
);
return
ret
;
return
nvec
<
0
?
nvec
:
0
;
}
/**
* qib_free_irq - Cleanup INTx and MSI interrupts
* @dd: valid pointer to qib dev data
*
* Since cleanup for INTx and MSI interrupts is trivial, have a common
* routine.
*
*/
void
qib_free_irq
(
struct
qib_devdata
*
dd
)
{
pci_free_irq
(
dd
->
pcidev
,
0
,
dd
);
pci_free_irq_vectors
(
dd
->
pcidev
);
}
/*
...
...
@@ -351,10 +340,10 @@ int qib_reinit_intr(struct qib_devdata *dd)
dd
->
msi_data
);
ret
=
1
;
bail:
if
(
!
ret
&&
(
dd
->
flags
&
QIB_HAS_INTX
))
{
qib_enable_intx
(
dd
);
qib_free_irq
(
dd
);
if
(
!
ret
&&
(
dd
->
flags
&
QIB_HAS_INTX
))
ret
=
1
;
}
/* and now set the pci master bit again */
pci_set_master
(
dd
->
pcidev
);
...
...
@@ -362,56 +351,6 @@ int qib_reinit_intr(struct qib_devdata *dd)
return
ret
;
}
/*
* Disable msi interrupt if enabled, and clear msi_lo.
* This is used primarily for the fallback to INTx, but
* is also used in reinit after reset, and during cleanup.
*/
void
qib_nomsi
(
struct
qib_devdata
*
dd
)
{
dd
->
msi_lo
=
0
;
pci_free_irq_vectors
(
dd
->
pcidev
);
}
/*
* Same as qib_nosmi, but for MSIx.
*/
void
qib_nomsix
(
struct
qib_devdata
*
dd
)
{
pci_free_irq_vectors
(
dd
->
pcidev
);
}
/*
* Similar to pci_intx(pdev, 1), except that we make sure
* msi(x) is off.
*/
void
qib_enable_intx
(
struct
qib_devdata
*
dd
)
{
u16
cw
,
new
;
int
pos
;
struct
pci_dev
*
pdev
=
dd
->
pcidev
;
if
(
pci_alloc_irq_vectors
(
pdev
,
1
,
1
,
PCI_IRQ_LEGACY
)
<
0
)
qib_dev_err
(
dd
,
"Failed to enable INTx
\n
"
);
pos
=
pdev
->
msi_cap
;
if
(
pos
)
{
/* then turn off MSI */
pci_read_config_word
(
pdev
,
pos
+
PCI_MSI_FLAGS
,
&
cw
);
new
=
cw
&
~
PCI_MSI_FLAGS_ENABLE
;
if
(
new
!=
cw
)
pci_write_config_word
(
pdev
,
pos
+
PCI_MSI_FLAGS
,
new
);
}
pos
=
pdev
->
msix_cap
;
if
(
pos
)
{
/* then turn off MSIx */
pci_read_config_word
(
pdev
,
pos
+
PCI_MSIX_FLAGS
,
&
cw
);
new
=
cw
&
~
PCI_MSIX_FLAGS_ENABLE
;
if
(
new
!=
cw
)
pci_write_config_word
(
pdev
,
pos
+
PCI_MSIX_FLAGS
,
new
);
}
}
/*
* These two routines are helper routines for the device reset code
* to move all the pcie code out of the chip-specific driver code.
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录