0001
0002
0003
0004
0005
0006
0007 #include <linux/kernel.h>
0008 #include <linux/fsl/mc.h>
0009
0010 #include "fsl-mc-private.h"
0011
0012
0013
0014
0015
0016 static u16 dprc_major_ver;
0017 static u16 dprc_minor_ver;
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030 int dprc_open(struct fsl_mc_io *mc_io,
0031 u32 cmd_flags,
0032 int container_id,
0033 u16 *token)
0034 {
0035 struct fsl_mc_command cmd = { 0 };
0036 struct dprc_cmd_open *cmd_params;
0037 int err;
0038
0039
0040 cmd.header = mc_encode_cmd_header(DPRC_CMDID_OPEN, cmd_flags,
0041 0);
0042 cmd_params = (struct dprc_cmd_open *)cmd.params;
0043 cmd_params->container_id = cpu_to_le32(container_id);
0044
0045
0046 err = mc_send_command(mc_io, &cmd);
0047 if (err)
0048 return err;
0049
0050
0051 *token = mc_cmd_hdr_read_token(&cmd);
0052
0053 return 0;
0054 }
0055 EXPORT_SYMBOL_GPL(dprc_open);
0056
0057
0058
0059
0060
0061
0062
0063
0064
0065
0066
0067
0068 int dprc_close(struct fsl_mc_io *mc_io,
0069 u32 cmd_flags,
0070 u16 token)
0071 {
0072 struct fsl_mc_command cmd = { 0 };
0073
0074
0075 cmd.header = mc_encode_cmd_header(DPRC_CMDID_CLOSE, cmd_flags,
0076 token);
0077
0078
0079 return mc_send_command(mc_io, &cmd);
0080 }
0081 EXPORT_SYMBOL_GPL(dprc_close);
0082
0083
0084
0085
0086
0087
0088
0089
0090
0091
0092
0093
0094
0095
0096
0097
0098
0099
0100
0101
0102
0103
0104
0105
0106
0107
0108
0109
0110
0111
0112 int dprc_reset_container(struct fsl_mc_io *mc_io,
0113 u32 cmd_flags,
0114 u16 token,
0115 int child_container_id,
0116 u32 options)
0117 {
0118 struct fsl_mc_command cmd = { 0 };
0119 struct dprc_cmd_reset_container *cmd_params;
0120 u32 cmdid = DPRC_CMDID_RESET_CONT;
0121 int err;
0122
0123
0124
0125
0126
0127 if (!dprc_major_ver && !dprc_minor_ver) {
0128 err = dprc_get_api_version(mc_io, 0,
0129 &dprc_major_ver,
0130 &dprc_minor_ver);
0131 if (err)
0132 return err;
0133 }
0134
0135
0136
0137
0138
0139
0140 if (dprc_major_ver > 6 || (dprc_major_ver == 6 && dprc_minor_ver >= 5))
0141 cmdid = DPRC_CMDID_RESET_CONT_V2;
0142
0143
0144 cmd.header = mc_encode_cmd_header(cmdid, cmd_flags, token);
0145 cmd_params = (struct dprc_cmd_reset_container *)cmd.params;
0146 cmd_params->child_container_id = cpu_to_le32(child_container_id);
0147 cmd_params->options = cpu_to_le32(options);
0148
0149
0150 return mc_send_command(mc_io, &cmd);
0151 }
0152 EXPORT_SYMBOL_GPL(dprc_reset_container);
0153
0154
0155
0156
0157
0158
0159
0160
0161
0162
0163
0164 int dprc_set_irq(struct fsl_mc_io *mc_io,
0165 u32 cmd_flags,
0166 u16 token,
0167 u8 irq_index,
0168 struct dprc_irq_cfg *irq_cfg)
0169 {
0170 struct fsl_mc_command cmd = { 0 };
0171 struct dprc_cmd_set_irq *cmd_params;
0172
0173
0174 cmd.header = mc_encode_cmd_header(DPRC_CMDID_SET_IRQ,
0175 cmd_flags,
0176 token);
0177 cmd_params = (struct dprc_cmd_set_irq *)cmd.params;
0178 cmd_params->irq_val = cpu_to_le32(irq_cfg->val);
0179 cmd_params->irq_index = irq_index;
0180 cmd_params->irq_addr = cpu_to_le64(irq_cfg->paddr);
0181 cmd_params->irq_num = cpu_to_le32(irq_cfg->irq_num);
0182
0183
0184 return mc_send_command(mc_io, &cmd);
0185 }
0186
0187
0188
0189
0190
0191
0192
0193
0194
0195
0196
0197
0198
0199
0200
0201
0202 int dprc_set_irq_enable(struct fsl_mc_io *mc_io,
0203 u32 cmd_flags,
0204 u16 token,
0205 u8 irq_index,
0206 u8 en)
0207 {
0208 struct fsl_mc_command cmd = { 0 };
0209 struct dprc_cmd_set_irq_enable *cmd_params;
0210
0211
0212 cmd.header = mc_encode_cmd_header(DPRC_CMDID_SET_IRQ_ENABLE,
0213 cmd_flags, token);
0214 cmd_params = (struct dprc_cmd_set_irq_enable *)cmd.params;
0215 cmd_params->enable = en & DPRC_ENABLE;
0216 cmd_params->irq_index = irq_index;
0217
0218
0219 return mc_send_command(mc_io, &cmd);
0220 }
0221
0222
0223
0224
0225
0226
0227
0228
0229
0230
0231
0232
0233
0234
0235
0236
0237
0238 int dprc_set_irq_mask(struct fsl_mc_io *mc_io,
0239 u32 cmd_flags,
0240 u16 token,
0241 u8 irq_index,
0242 u32 mask)
0243 {
0244 struct fsl_mc_command cmd = { 0 };
0245 struct dprc_cmd_set_irq_mask *cmd_params;
0246
0247
0248 cmd.header = mc_encode_cmd_header(DPRC_CMDID_SET_IRQ_MASK,
0249 cmd_flags, token);
0250 cmd_params = (struct dprc_cmd_set_irq_mask *)cmd.params;
0251 cmd_params->mask = cpu_to_le32(mask);
0252 cmd_params->irq_index = irq_index;
0253
0254
0255 return mc_send_command(mc_io, &cmd);
0256 }
0257
0258
0259
0260
0261
0262
0263
0264
0265
0266
0267
0268
0269
0270 int dprc_get_irq_status(struct fsl_mc_io *mc_io,
0271 u32 cmd_flags,
0272 u16 token,
0273 u8 irq_index,
0274 u32 *status)
0275 {
0276 struct fsl_mc_command cmd = { 0 };
0277 struct dprc_cmd_get_irq_status *cmd_params;
0278 struct dprc_rsp_get_irq_status *rsp_params;
0279 int err;
0280
0281
0282 cmd.header = mc_encode_cmd_header(DPRC_CMDID_GET_IRQ_STATUS,
0283 cmd_flags, token);
0284 cmd_params = (struct dprc_cmd_get_irq_status *)cmd.params;
0285 cmd_params->status = cpu_to_le32(*status);
0286 cmd_params->irq_index = irq_index;
0287
0288
0289 err = mc_send_command(mc_io, &cmd);
0290 if (err)
0291 return err;
0292
0293
0294 rsp_params = (struct dprc_rsp_get_irq_status *)cmd.params;
0295 *status = le32_to_cpu(rsp_params->status);
0296
0297 return 0;
0298 }
0299
0300
0301
0302
0303
0304
0305
0306
0307
0308
0309
0310
0311
0312 int dprc_clear_irq_status(struct fsl_mc_io *mc_io,
0313 u32 cmd_flags,
0314 u16 token,
0315 u8 irq_index,
0316 u32 status)
0317 {
0318 struct fsl_mc_command cmd = { 0 };
0319 struct dprc_cmd_clear_irq_status *cmd_params;
0320
0321
0322 cmd.header = mc_encode_cmd_header(DPRC_CMDID_CLEAR_IRQ_STATUS,
0323 cmd_flags, token);
0324 cmd_params = (struct dprc_cmd_clear_irq_status *)cmd.params;
0325 cmd_params->status = cpu_to_le32(status);
0326 cmd_params->irq_index = irq_index;
0327
0328
0329 return mc_send_command(mc_io, &cmd);
0330 }
0331
0332
0333
0334
0335
0336
0337
0338
0339
0340
0341 int dprc_get_attributes(struct fsl_mc_io *mc_io,
0342 u32 cmd_flags,
0343 u16 token,
0344 struct dprc_attributes *attr)
0345 {
0346 struct fsl_mc_command cmd = { 0 };
0347 struct dprc_rsp_get_attributes *rsp_params;
0348 int err;
0349
0350
0351 cmd.header = mc_encode_cmd_header(DPRC_CMDID_GET_ATTR,
0352 cmd_flags,
0353 token);
0354
0355
0356 err = mc_send_command(mc_io, &cmd);
0357 if (err)
0358 return err;
0359
0360
0361 rsp_params = (struct dprc_rsp_get_attributes *)cmd.params;
0362 attr->container_id = le32_to_cpu(rsp_params->container_id);
0363 attr->icid = le32_to_cpu(rsp_params->icid);
0364 attr->options = le32_to_cpu(rsp_params->options);
0365 attr->portal_id = le32_to_cpu(rsp_params->portal_id);
0366
0367 return 0;
0368 }
0369
0370
0371
0372
0373
0374
0375
0376
0377
0378
0379 int dprc_get_obj_count(struct fsl_mc_io *mc_io,
0380 u32 cmd_flags,
0381 u16 token,
0382 int *obj_count)
0383 {
0384 struct fsl_mc_command cmd = { 0 };
0385 struct dprc_rsp_get_obj_count *rsp_params;
0386 int err;
0387
0388
0389 cmd.header = mc_encode_cmd_header(DPRC_CMDID_GET_OBJ_COUNT,
0390 cmd_flags, token);
0391
0392
0393 err = mc_send_command(mc_io, &cmd);
0394 if (err)
0395 return err;
0396
0397
0398 rsp_params = (struct dprc_rsp_get_obj_count *)cmd.params;
0399 *obj_count = le32_to_cpu(rsp_params->obj_count);
0400
0401 return 0;
0402 }
0403 EXPORT_SYMBOL_GPL(dprc_get_obj_count);
0404
0405
0406
0407
0408
0409
0410
0411
0412
0413
0414
0415
0416
0417
0418
0419
0420 int dprc_get_obj(struct fsl_mc_io *mc_io,
0421 u32 cmd_flags,
0422 u16 token,
0423 int obj_index,
0424 struct fsl_mc_obj_desc *obj_desc)
0425 {
0426 struct fsl_mc_command cmd = { 0 };
0427 struct dprc_cmd_get_obj *cmd_params;
0428 struct dprc_rsp_get_obj *rsp_params;
0429 int err;
0430
0431
0432 cmd.header = mc_encode_cmd_header(DPRC_CMDID_GET_OBJ,
0433 cmd_flags,
0434 token);
0435 cmd_params = (struct dprc_cmd_get_obj *)cmd.params;
0436 cmd_params->obj_index = cpu_to_le32(obj_index);
0437
0438
0439 err = mc_send_command(mc_io, &cmd);
0440 if (err)
0441 return err;
0442
0443
0444 rsp_params = (struct dprc_rsp_get_obj *)cmd.params;
0445 obj_desc->id = le32_to_cpu(rsp_params->id);
0446 obj_desc->vendor = le16_to_cpu(rsp_params->vendor);
0447 obj_desc->irq_count = rsp_params->irq_count;
0448 obj_desc->region_count = rsp_params->region_count;
0449 obj_desc->state = le32_to_cpu(rsp_params->state);
0450 obj_desc->ver_major = le16_to_cpu(rsp_params->version_major);
0451 obj_desc->ver_minor = le16_to_cpu(rsp_params->version_minor);
0452 obj_desc->flags = le16_to_cpu(rsp_params->flags);
0453 strncpy(obj_desc->type, rsp_params->type, 16);
0454 obj_desc->type[15] = '\0';
0455 strncpy(obj_desc->label, rsp_params->label, 16);
0456 obj_desc->label[15] = '\0';
0457 return 0;
0458 }
0459 EXPORT_SYMBOL_GPL(dprc_get_obj);
0460
0461
0462
0463
0464
0465
0466
0467
0468
0469
0470
0471
0472
0473 int dprc_set_obj_irq(struct fsl_mc_io *mc_io,
0474 u32 cmd_flags,
0475 u16 token,
0476 char *obj_type,
0477 int obj_id,
0478 u8 irq_index,
0479 struct dprc_irq_cfg *irq_cfg)
0480 {
0481 struct fsl_mc_command cmd = { 0 };
0482 struct dprc_cmd_set_obj_irq *cmd_params;
0483
0484
0485 cmd.header = mc_encode_cmd_header(DPRC_CMDID_SET_OBJ_IRQ,
0486 cmd_flags,
0487 token);
0488 cmd_params = (struct dprc_cmd_set_obj_irq *)cmd.params;
0489 cmd_params->irq_val = cpu_to_le32(irq_cfg->val);
0490 cmd_params->irq_index = irq_index;
0491 cmd_params->irq_addr = cpu_to_le64(irq_cfg->paddr);
0492 cmd_params->irq_num = cpu_to_le32(irq_cfg->irq_num);
0493 cmd_params->obj_id = cpu_to_le32(obj_id);
0494 strncpy(cmd_params->obj_type, obj_type, 16);
0495 cmd_params->obj_type[15] = '\0';
0496
0497
0498 return mc_send_command(mc_io, &cmd);
0499 }
0500 EXPORT_SYMBOL_GPL(dprc_set_obj_irq);
0501
0502
0503
0504
0505
0506
0507
0508
0509
0510
0511
0512
0513
0514 int dprc_get_obj_region(struct fsl_mc_io *mc_io,
0515 u32 cmd_flags,
0516 u16 token,
0517 char *obj_type,
0518 int obj_id,
0519 u8 region_index,
0520 struct dprc_region_desc *region_desc)
0521 {
0522 struct fsl_mc_command cmd = { 0 };
0523 struct dprc_cmd_get_obj_region *cmd_params;
0524 struct dprc_rsp_get_obj_region *rsp_params;
0525 int err;
0526
0527
0528
0529
0530
0531 if (!dprc_major_ver && !dprc_minor_ver) {
0532 err = dprc_get_api_version(mc_io, 0,
0533 &dprc_major_ver,
0534 &dprc_minor_ver);
0535 if (err)
0536 return err;
0537 }
0538
0539 if (dprc_major_ver > 6 || (dprc_major_ver == 6 && dprc_minor_ver >= 6)) {
0540
0541
0542
0543
0544
0545
0546
0547 cmd.header = mc_encode_cmd_header(DPRC_CMDID_GET_OBJ_REG_V3,
0548 cmd_flags, token);
0549
0550 } else if (dprc_major_ver == 6 && dprc_minor_ver >= 3) {
0551
0552
0553
0554
0555
0556
0557 cmd.header = mc_encode_cmd_header(DPRC_CMDID_GET_OBJ_REG_V2,
0558 cmd_flags, token);
0559 } else {
0560 cmd.header = mc_encode_cmd_header(DPRC_CMDID_GET_OBJ_REG,
0561 cmd_flags, token);
0562 }
0563
0564 cmd_params = (struct dprc_cmd_get_obj_region *)cmd.params;
0565 cmd_params->obj_id = cpu_to_le32(obj_id);
0566 cmd_params->region_index = region_index;
0567 strncpy(cmd_params->obj_type, obj_type, 16);
0568 cmd_params->obj_type[15] = '\0';
0569
0570
0571 err = mc_send_command(mc_io, &cmd);
0572 if (err)
0573 return err;
0574
0575
0576 rsp_params = (struct dprc_rsp_get_obj_region *)cmd.params;
0577 region_desc->base_offset = le64_to_cpu(rsp_params->base_offset);
0578 region_desc->size = le32_to_cpu(rsp_params->size);
0579 region_desc->type = rsp_params->type;
0580 region_desc->flags = le32_to_cpu(rsp_params->flags);
0581 if (dprc_major_ver > 6 || (dprc_major_ver == 6 && dprc_minor_ver >= 3))
0582 region_desc->base_address = le64_to_cpu(rsp_params->base_addr);
0583 else
0584 region_desc->base_address = 0;
0585
0586 return 0;
0587 }
0588 EXPORT_SYMBOL_GPL(dprc_get_obj_region);
0589
0590
0591
0592
0593
0594
0595
0596
0597
0598
0599 int dprc_get_api_version(struct fsl_mc_io *mc_io,
0600 u32 cmd_flags,
0601 u16 *major_ver,
0602 u16 *minor_ver)
0603 {
0604 struct fsl_mc_command cmd = { 0 };
0605 int err;
0606
0607
0608 cmd.header = mc_encode_cmd_header(DPRC_CMDID_GET_API_VERSION,
0609 cmd_flags, 0);
0610
0611
0612 err = mc_send_command(mc_io, &cmd);
0613 if (err)
0614 return err;
0615
0616
0617 mc_cmd_read_api_version(&cmd, major_ver, minor_ver);
0618
0619 return 0;
0620 }
0621
0622
0623
0624
0625
0626
0627
0628
0629
0630 int dprc_get_container_id(struct fsl_mc_io *mc_io,
0631 u32 cmd_flags,
0632 int *container_id)
0633 {
0634 struct fsl_mc_command cmd = { 0 };
0635 int err;
0636
0637
0638 cmd.header = mc_encode_cmd_header(DPRC_CMDID_GET_CONT_ID,
0639 cmd_flags,
0640 0);
0641
0642
0643 err = mc_send_command(mc_io, &cmd);
0644 if (err)
0645 return err;
0646
0647
0648 *container_id = (int)mc_cmd_read_object_id(&cmd);
0649
0650 return 0;
0651 }
0652
0653
0654
0655
0656
0657
0658
0659
0660
0661
0662
0663
0664
0665
0666
0667
0668 int dprc_get_connection(struct fsl_mc_io *mc_io,
0669 u32 cmd_flags,
0670 u16 token,
0671 const struct dprc_endpoint *endpoint1,
0672 struct dprc_endpoint *endpoint2,
0673 int *state)
0674 {
0675 struct dprc_cmd_get_connection *cmd_params;
0676 struct dprc_rsp_get_connection *rsp_params;
0677 struct fsl_mc_command cmd = { 0 };
0678 int err, i;
0679
0680
0681 cmd.header = mc_encode_cmd_header(DPRC_CMDID_GET_CONNECTION,
0682 cmd_flags,
0683 token);
0684 cmd_params = (struct dprc_cmd_get_connection *)cmd.params;
0685 cmd_params->ep1_id = cpu_to_le32(endpoint1->id);
0686 cmd_params->ep1_interface_id = cpu_to_le16(endpoint1->if_id);
0687 for (i = 0; i < 16; i++)
0688 cmd_params->ep1_type[i] = endpoint1->type[i];
0689
0690
0691 err = mc_send_command(mc_io, &cmd);
0692 if (err)
0693 return -ENOTCONN;
0694
0695
0696 rsp_params = (struct dprc_rsp_get_connection *)cmd.params;
0697 endpoint2->id = le32_to_cpu(rsp_params->ep2_id);
0698 endpoint2->if_id = le16_to_cpu(rsp_params->ep2_interface_id);
0699 *state = le32_to_cpu(rsp_params->state);
0700 for (i = 0; i < 16; i++)
0701 endpoint2->type[i] = rsp_params->ep2_type[i];
0702
0703 return 0;
0704 }