diff options
author | Haiying Wang <Haiying.Wang@freescale.com> | 2013-10-18 19:27:13 (GMT) |
---|---|---|
committer | J. German Rivera <German.Rivera@freescale.com> | 2013-10-22 20:14:50 (GMT) |
commit | 79bd27e905da1b17a17ea807c04dc7fddd0dcb14 (patch) | |
tree | 6ece4e072fe0590331e1692289caf5fc9744ea1e /drivers | |
parent | c0e2e95af2c30aaf2161633623d3f32f91403071 (diff) | |
download | linux-fsl-qoriq-79bd27e905da1b17a17ea807c04dc7fddd0dcb14.tar.xz |
fsl_qman: add APIs to set CQ CR/ER eligibility within the channel
Signed-off-by: Haiying Wang <Haiying.Wang@freescale.com>
Change-Id: I1ba0d8eb5f0a5c4b1b7156e2556253b916d351e9
Reviewed-on: http://git.am.freescale.net:8181/5871
Tested-by: Review Code-CDREVIEW <CDREVIEW@freescale.com>
Reviewed-by: Thorpe Geoff-R01361 <Geoff.Thorpe@freescale.com>
Reviewed-by: Rivera Jose-B46482 <German.Rivera@freescale.com>
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/staging/fsl_qbman/qman_high.c | 221 |
1 files changed, 142 insertions, 79 deletions
diff --git a/drivers/staging/fsl_qbman/qman_high.c b/drivers/staging/fsl_qbman/qman_high.c index 00ecab8..af190cd 100644 --- a/drivers/staging/fsl_qbman/qman_high.c +++ b/drivers/staging/fsl_qbman/qman_high.c @@ -4001,18 +4001,154 @@ int qman_ceetm_channel_get_group(struct qm_ceetm_channel *channel, int *group_b, } EXPORT_SYMBOL(qman_ceetm_channel_get_group); -#define CQ_ELIGIBILITY_MASK(n) (1 << (7 - n)) -#define CQ_A_ELIGIBILITY_MASK (1 << 8) -#define CQ_B_ELIGIBILITY_MASK (1 << 9) +#define GROUP_A_ELIGIBILITY_SET (1 << 8) +#define GROUP_B_ELIGIBILITY_SET (1 << 9) +#define CQ_ELIGIBILITY_SET(n) (1 << (7 - n)) +int qman_ceetm_channel_set_group_cr_eligibility(struct qm_ceetm_channel + *channel, int group_b, int cre) +{ + struct qm_mcc_ceetm_class_scheduler_config csch_config; + struct qm_mcr_ceetm_class_scheduler_query csch_query; + int i; + + if (qman_ceetm_query_class_scheduler(channel, &csch_query)) { + pr_err("Cannot get the channel %d scheduler setting.\n", + channel->idx); + return -EINVAL; + } + csch_config.cqcid = channel->idx; + csch_config.dcpid = channel->dcp_idx; + csch_config.gpc = csch_query.gpc; + for (i = 0; i < 8; i++) + csch_config.w[i] = csch_query.w[i]; + csch_config.erem = csch_query.erem; + if (group_b) + csch_config.crem = (csch_query.crem & ~GROUP_B_ELIGIBILITY_SET) + | (cre ? GROUP_B_ELIGIBILITY_SET : 0); + else + csch_config.crem = (csch_query.crem & ~GROUP_A_ELIGIBILITY_SET) + | (cre ? GROUP_A_ELIGIBILITY_SET : 0); + + if (qman_ceetm_configure_class_scheduler(&csch_config)) { + pr_err("Cannot config channel %d's scheduler with " + "group_%c's cr eligibility\n", channel->idx, + group_b ? 'b' : 'a'); + return -EINVAL; + } + + return 0; +} +EXPORT_SYMBOL(qman_ceetm_channel_set_group_cr_eligibility); + +int qman_ceetm_channel_set_group_er_eligibility(struct qm_ceetm_channel + *channel, int group_b, int ere) +{ + struct qm_mcc_ceetm_class_scheduler_config csch_config; + struct qm_mcr_ceetm_class_scheduler_query csch_query; + int i; + + if (qman_ceetm_query_class_scheduler(channel, &csch_query)) { + pr_err("Cannot get the channel %d scheduler setting.\n", + channel->idx); + return -EINVAL; + } + csch_config.cqcid = channel->idx; + csch_config.dcpid = channel->dcp_idx; + csch_config.gpc = csch_query.gpc; + for (i = 0; i < 8; i++) + csch_config.w[i] = csch_query.w[i]; + csch_config.crem = csch_query.crem; + if (group_b) + csch_config.erem = (csch_query.erem & ~GROUP_B_ELIGIBILITY_SET) + | (ere ? GROUP_B_ELIGIBILITY_SET : 0); + else + csch_config.erem = (csch_query.erem & ~GROUP_A_ELIGIBILITY_SET) + | (ere ? GROUP_A_ELIGIBILITY_SET : 0); + + if (qman_ceetm_configure_class_scheduler(&csch_config)) { + pr_err("Cannot config channel %d's scheduler with " + "group_%c's er eligibility\n", channel->idx, + group_b ? 'b' : 'a'); + return -EINVAL; + } + + return 0; +} +EXPORT_SYMBOL(qman_ceetm_channel_set_group_er_eligibility); + +int qman_ceetm_channel_set_cq_cr_eligibility(struct qm_ceetm_channel *channel, + unsigned int idx, u16 cre) +{ + struct qm_mcc_ceetm_class_scheduler_config csch_config; + struct qm_mcr_ceetm_class_scheduler_query csch_query; + int i; + + if (idx > 7) { + pr_err("CQ index is out of range\n"); + return -EINVAL; + } + if (qman_ceetm_query_class_scheduler(channel, &csch_query)) { + pr_err("Cannot get the channel %d scheduler setting.\n", + channel->idx); + return -EINVAL; + } + csch_config.cqcid = channel->idx; + csch_config.dcpid = channel->dcp_idx; + csch_config.gpc = csch_query.gpc; + for (i = 0; i < 8; i++) + csch_config.w[i] = csch_query.w[i]; + csch_config.erem = csch_query.erem; + csch_config.crem = (csch_query.crem & ~CQ_ELIGIBILITY_SET(idx)) | + (cre ? CQ_ELIGIBILITY_SET(idx) : 0); + if (qman_ceetm_configure_class_scheduler(&csch_config)) { + pr_err("Cannot config channel scheduler to set " + "cr eligibility mask for CQ#%d\n", idx); + return -EINVAL; + } + + return 0; +} +EXPORT_SYMBOL(qman_ceetm_channel_set_cq_cr_eligibility); + +int qman_ceetm_channel_set_cq_er_eligibility(struct qm_ceetm_channel *channel, + unsigned int idx, u16 ere) +{ + struct qm_mcc_ceetm_class_scheduler_config csch_config; + struct qm_mcr_ceetm_class_scheduler_query csch_query; + int i; + + if (idx > 7) { + pr_err("CQ index is out of range\n"); + return -EINVAL; + } + if (qman_ceetm_query_class_scheduler(channel, &csch_query)) { + pr_err("Cannot get the channel %d scheduler setting.\n", + channel->idx); + return -EINVAL; + } + csch_config.cqcid = channel->idx; + csch_config.dcpid = channel->dcp_idx; + csch_config.gpc = csch_query.gpc; + for (i = 0; i < 8; i++) + csch_config.w[i] = csch_query.w[i]; + csch_config.crem = csch_query.crem; + csch_config.erem = (csch_query.erem & ~CQ_ELIGIBILITY_SET(idx)) | + (ere ? CQ_ELIGIBILITY_SET(idx) : 0); + if (qman_ceetm_configure_class_scheduler(&csch_config)) { + pr_err("Cannot config channel scheduler to set " + "er eligibility mask for CQ#%d\n", idx); + return -EINVAL; + } + return 0; +} +EXPORT_SYMBOL(qman_ceetm_channel_set_cq_er_eligibility); + int qman_ceetm_cq_claim(struct qm_ceetm_cq **cq, struct qm_ceetm_channel *channel, unsigned int idx, struct qm_ceetm_ccg *ccg) { struct qm_ceetm_cq *p; struct qm_mcc_ceetm_cq_config cq_config; - struct qm_mcc_ceetm_class_scheduler_config csch_config; - struct qm_mcr_ceetm_class_scheduler_query csch_query_result; - int i; if (idx > 7) { pr_err("The independent class queue id is out of range\n"); @@ -4049,29 +4185,6 @@ int qman_ceetm_cq_claim(struct qm_ceetm_cq **cq, } } - if (channel->shaper_enable) { - if (qman_ceetm_query_class_scheduler(channel, - &csch_query_result)) { - pr_err("Can't query channel#%d!\n", channel->idx); - return -EINVAL; - } - csch_config.cqcid = channel->idx; - csch_config.dcpid = channel->dcp_idx; - csch_config.crem = csch_query_result.crem | - CQ_ELIGIBILITY_MASK(idx); - csch_config.erem = csch_query_result.erem | - CQ_ELIGIBILITY_MASK(idx); - csch_config.gpc = csch_query_result.gpc; - for (i = 0; i < 8; i++) - csch_config.w[i] = csch_query_result.w[i]; - - if (qman_ceetm_configure_class_scheduler(&csch_config)) { - pr_err("Can't config channel scheduler to set" - " eligibility mask for CQ#%d\n", idx); - return -EINVAL; - } - } - *cq = p; return 0; } @@ -4083,9 +4196,6 @@ int qman_ceetm_cq_claim_A(struct qm_ceetm_cq **cq, { struct qm_ceetm_cq *p; struct qm_mcc_ceetm_cq_config cq_config; - struct qm_mcc_ceetm_class_scheduler_config csch_config; - struct qm_mcr_ceetm_class_scheduler_query csch_query_result; - int i; if ((idx < 7) || (idx > 15)) { pr_err("This grouped class queue id is out of range\n"); @@ -4121,28 +4231,6 @@ int qman_ceetm_cq_claim_A(struct qm_ceetm_cq **cq, return -EINVAL; } } - - if (channel->shaper_enable) { - if (qman_ceetm_query_class_scheduler(channel, - &csch_query_result)) { - pr_err("Can't query channel#%d!\n", channel->idx); - return -EINVAL; - } - csch_config.cqcid = channel->idx; - csch_config.dcpid = channel->dcp_idx; - csch_config.crem = csch_query_result.crem | - CQ_A_ELIGIBILITY_MASK; - csch_config.erem = csch_query_result.erem | - CQ_A_ELIGIBILITY_MASK; - csch_config.gpc = csch_query_result.gpc; - for (i = 0; i < 8; i++) - csch_config.w[i] = csch_query_result.w[i]; - if (qman_ceetm_configure_class_scheduler(&csch_config)) { - pr_err("Can't config channel scheduler to set" - " eligibility mask for CQ#%d\n", idx); - return -EINVAL; - } - } *cq = p; return 0; } @@ -4154,9 +4242,6 @@ int qman_ceetm_cq_claim_B(struct qm_ceetm_cq **cq, { struct qm_ceetm_cq *p; struct qm_mcc_ceetm_cq_config cq_config; - struct qm_mcc_ceetm_class_scheduler_config csch_config; - struct qm_mcr_ceetm_class_scheduler_query csch_query_result; - int i; if ((idx < 11) || (idx > 15)) { pr_err("This grouped class queue id is out of range\n"); @@ -4192,28 +4277,6 @@ int qman_ceetm_cq_claim_B(struct qm_ceetm_cq **cq, return -EINVAL; } } - - if (channel->shaper_enable) { - if (qman_ceetm_query_class_scheduler(channel, - &csch_query_result)) { - pr_err("Can't query channel#%d!\n", channel->idx); - return -EINVAL; - } - csch_config.cqcid = channel->idx; - csch_config.dcpid = channel->dcp_idx; - csch_config.crem = csch_query_result.crem | - CQ_B_ELIGIBILITY_MASK; - csch_config.erem = csch_query_result.erem | - CQ_B_ELIGIBILITY_MASK; - csch_config.gpc = csch_query_result.gpc; - for (i = 0; i < 8; i++) - csch_config.w[i] = csch_query_result.w[i]; - if (qman_ceetm_configure_class_scheduler(&csch_config)) { - pr_err("Can't config channel scheduler to set" - " eligibility mask for CQ#%d\n", idx); - return -EINVAL; - } - } *cq = p; return 0; } |