0001
0002
0003
0004
0005
0006 #include <linux/delay.h>
0007 #include <linux/kernel.h>
0008 #include <linux/module.h>
0009 #include <linux/of.h>
0010 #include <linux/platform_data/cros_ec_commands.h>
0011 #include <linux/platform_data/cros_ec_proto.h>
0012 #include <linux/platform_device.h>
0013 #include <linux/slab.h>
0014 #include <linux/spi/spi.h>
0015 #include <uapi/linux/sched/types.h>
0016
0017 #include "cros_ec.h"
0018
0019
0020 #define EC_MSG_HEADER 0xec
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031 #define EC_MSG_PREAMBLE_COUNT 32
0032
0033
0034
0035
0036
0037
0038
0039
0040
0041
0042
0043
0044
0045
0046
0047
0048
0049
0050
0051
0052 #define EC_MSG_DEADLINE_MS 200
0053
0054
0055
0056
0057
0058
0059
0060
0061 #define EC_SPI_RECOVERY_TIME_NS (200 * 1000)
0062
0063
0064
0065
0066
0067
0068
0069
0070
0071
0072
0073
0074 struct cros_ec_spi {
0075 struct spi_device *spi;
0076 s64 last_transfer_ns;
0077 unsigned int start_of_msg_delay;
0078 unsigned int end_of_msg_delay;
0079 struct kthread_worker *high_pri_worker;
0080 };
0081
0082 typedef int (*cros_ec_xfer_fn_t) (struct cros_ec_device *ec_dev,
0083 struct cros_ec_command *ec_msg);
0084
0085
0086
0087
0088
0089
0090
0091
0092
0093
0094
0095 struct cros_ec_xfer_work_params {
0096 struct kthread_work work;
0097 cros_ec_xfer_fn_t fn;
0098 struct cros_ec_device *ec_dev;
0099 struct cros_ec_command *ec_msg;
0100 int ret;
0101 };
0102
0103 static void debug_packet(struct device *dev, const char *name, u8 *ptr,
0104 int len)
0105 {
0106 #ifdef DEBUG
0107 int i;
0108
0109 dev_dbg(dev, "%s: ", name);
0110 for (i = 0; i < len; i++)
0111 pr_cont(" %02x", ptr[i]);
0112
0113 pr_cont("\n");
0114 #endif
0115 }
0116
0117 static int terminate_request(struct cros_ec_device *ec_dev)
0118 {
0119 struct cros_ec_spi *ec_spi = ec_dev->priv;
0120 struct spi_message msg;
0121 struct spi_transfer trans;
0122 int ret;
0123
0124
0125
0126
0127
0128 spi_message_init(&msg);
0129 memset(&trans, 0, sizeof(trans));
0130 trans.delay.value = ec_spi->end_of_msg_delay;
0131 trans.delay.unit = SPI_DELAY_UNIT_USECS;
0132 spi_message_add_tail(&trans, &msg);
0133
0134 ret = spi_sync_locked(ec_spi->spi, &msg);
0135
0136
0137 ec_spi->last_transfer_ns = ktime_get_ns();
0138 if (ret < 0) {
0139 dev_err(ec_dev->dev,
0140 "cs-deassert spi transfer failed: %d\n",
0141 ret);
0142 }
0143
0144 return ret;
0145 }
0146
0147
0148
0149
0150
0151
0152
0153
0154
0155
0156 static int receive_n_bytes(struct cros_ec_device *ec_dev, u8 *buf, int n)
0157 {
0158 struct cros_ec_spi *ec_spi = ec_dev->priv;
0159 struct spi_transfer trans;
0160 struct spi_message msg;
0161 int ret;
0162
0163 if (buf - ec_dev->din + n > ec_dev->din_size)
0164 return -EINVAL;
0165
0166 memset(&trans, 0, sizeof(trans));
0167 trans.cs_change = 1;
0168 trans.rx_buf = buf;
0169 trans.len = n;
0170
0171 spi_message_init(&msg);
0172 spi_message_add_tail(&trans, &msg);
0173 ret = spi_sync_locked(ec_spi->spi, &msg);
0174 if (ret < 0)
0175 dev_err(ec_dev->dev, "spi transfer failed: %d\n", ret);
0176
0177 return ret;
0178 }
0179
0180
0181
0182
0183
0184
0185
0186
0187
0188
0189
0190
0191
0192 static int cros_ec_spi_receive_packet(struct cros_ec_device *ec_dev,
0193 int need_len)
0194 {
0195 struct ec_host_response *response;
0196 u8 *ptr, *end;
0197 int ret;
0198 unsigned long deadline;
0199 int todo;
0200
0201 if (ec_dev->din_size < EC_MSG_PREAMBLE_COUNT)
0202 return -EINVAL;
0203
0204
0205 deadline = jiffies + msecs_to_jiffies(EC_MSG_DEADLINE_MS);
0206 while (true) {
0207 unsigned long start_jiffies = jiffies;
0208
0209 ret = receive_n_bytes(ec_dev,
0210 ec_dev->din,
0211 EC_MSG_PREAMBLE_COUNT);
0212 if (ret < 0)
0213 return ret;
0214
0215 ptr = ec_dev->din;
0216 for (end = ptr + EC_MSG_PREAMBLE_COUNT; ptr != end; ptr++) {
0217 if (*ptr == EC_SPI_FRAME_START) {
0218 dev_dbg(ec_dev->dev, "msg found at %zd\n",
0219 ptr - ec_dev->din);
0220 break;
0221 }
0222 }
0223 if (ptr != end)
0224 break;
0225
0226
0227
0228
0229
0230
0231 if (time_after(start_jiffies, deadline)) {
0232 dev_warn(ec_dev->dev, "EC failed to respond in time\n");
0233 return -ETIMEDOUT;
0234 }
0235 }
0236
0237
0238
0239
0240
0241 todo = end - ++ptr;
0242 todo = min(todo, need_len);
0243 memmove(ec_dev->din, ptr, todo);
0244 ptr = ec_dev->din + todo;
0245 dev_dbg(ec_dev->dev, "need %d, got %d bytes from preamble\n",
0246 need_len, todo);
0247 need_len -= todo;
0248
0249
0250 if (todo < sizeof(*response)) {
0251 ret = receive_n_bytes(ec_dev, ptr, sizeof(*response) - todo);
0252 if (ret < 0)
0253 return -EBADMSG;
0254 ptr += (sizeof(*response) - todo);
0255 todo = sizeof(*response);
0256 }
0257
0258 response = (struct ec_host_response *)ec_dev->din;
0259
0260
0261 if (response->data_len > ec_dev->din_size)
0262 return -EMSGSIZE;
0263
0264
0265 while (need_len > 0) {
0266
0267
0268
0269
0270
0271
0272 todo = min(need_len, 256);
0273 dev_dbg(ec_dev->dev, "loop, todo=%d, need_len=%d, ptr=%zd\n",
0274 todo, need_len, ptr - ec_dev->din);
0275
0276 ret = receive_n_bytes(ec_dev, ptr, todo);
0277 if (ret < 0)
0278 return ret;
0279
0280 ptr += todo;
0281 need_len -= todo;
0282 }
0283
0284 dev_dbg(ec_dev->dev, "loop done, ptr=%zd\n", ptr - ec_dev->din);
0285
0286 return 0;
0287 }
0288
0289
0290
0291
0292
0293
0294
0295
0296
0297
0298
0299
0300
0301 static int cros_ec_spi_receive_response(struct cros_ec_device *ec_dev,
0302 int need_len)
0303 {
0304 u8 *ptr, *end;
0305 int ret;
0306 unsigned long deadline;
0307 int todo;
0308
0309 if (ec_dev->din_size < EC_MSG_PREAMBLE_COUNT)
0310 return -EINVAL;
0311
0312
0313 deadline = jiffies + msecs_to_jiffies(EC_MSG_DEADLINE_MS);
0314 while (true) {
0315 unsigned long start_jiffies = jiffies;
0316
0317 ret = receive_n_bytes(ec_dev,
0318 ec_dev->din,
0319 EC_MSG_PREAMBLE_COUNT);
0320 if (ret < 0)
0321 return ret;
0322
0323 ptr = ec_dev->din;
0324 for (end = ptr + EC_MSG_PREAMBLE_COUNT; ptr != end; ptr++) {
0325 if (*ptr == EC_SPI_FRAME_START) {
0326 dev_dbg(ec_dev->dev, "msg found at %zd\n",
0327 ptr - ec_dev->din);
0328 break;
0329 }
0330 }
0331 if (ptr != end)
0332 break;
0333
0334
0335
0336
0337
0338
0339 if (time_after(start_jiffies, deadline)) {
0340 dev_warn(ec_dev->dev, "EC failed to respond in time\n");
0341 return -ETIMEDOUT;
0342 }
0343 }
0344
0345
0346
0347
0348
0349 todo = end - ++ptr;
0350 todo = min(todo, need_len);
0351 memmove(ec_dev->din, ptr, todo);
0352 ptr = ec_dev->din + todo;
0353 dev_dbg(ec_dev->dev, "need %d, got %d bytes from preamble\n",
0354 need_len, todo);
0355 need_len -= todo;
0356
0357
0358 while (need_len > 0) {
0359
0360
0361
0362
0363
0364
0365 todo = min(need_len, 256);
0366 dev_dbg(ec_dev->dev, "loop, todo=%d, need_len=%d, ptr=%zd\n",
0367 todo, need_len, ptr - ec_dev->din);
0368
0369 ret = receive_n_bytes(ec_dev, ptr, todo);
0370 if (ret < 0)
0371 return ret;
0372
0373 debug_packet(ec_dev->dev, "interim", ptr, todo);
0374 ptr += todo;
0375 need_len -= todo;
0376 }
0377
0378 dev_dbg(ec_dev->dev, "loop done, ptr=%zd\n", ptr - ec_dev->din);
0379
0380 return 0;
0381 }
0382
0383
0384
0385
0386
0387
0388
0389 static int do_cros_ec_pkt_xfer_spi(struct cros_ec_device *ec_dev,
0390 struct cros_ec_command *ec_msg)
0391 {
0392 struct ec_host_response *response;
0393 struct cros_ec_spi *ec_spi = ec_dev->priv;
0394 struct spi_transfer trans, trans_delay;
0395 struct spi_message msg;
0396 int i, len;
0397 u8 *ptr;
0398 u8 *rx_buf;
0399 u8 sum;
0400 u8 rx_byte;
0401 int ret = 0, final_ret;
0402 unsigned long delay;
0403
0404 len = cros_ec_prepare_tx(ec_dev, ec_msg);
0405 if (len < 0)
0406 return len;
0407 dev_dbg(ec_dev->dev, "prepared, len=%d\n", len);
0408
0409
0410 delay = ktime_get_ns() - ec_spi->last_transfer_ns;
0411 if (delay < EC_SPI_RECOVERY_TIME_NS)
0412 ndelay(EC_SPI_RECOVERY_TIME_NS - delay);
0413
0414 rx_buf = kzalloc(len, GFP_KERNEL);
0415 if (!rx_buf)
0416 return -ENOMEM;
0417
0418 spi_bus_lock(ec_spi->spi->master);
0419
0420
0421
0422
0423
0424 spi_message_init(&msg);
0425 if (ec_spi->start_of_msg_delay) {
0426 memset(&trans_delay, 0, sizeof(trans_delay));
0427 trans_delay.delay.value = ec_spi->start_of_msg_delay;
0428 trans_delay.delay.unit = SPI_DELAY_UNIT_USECS;
0429 spi_message_add_tail(&trans_delay, &msg);
0430 }
0431
0432
0433 memset(&trans, 0, sizeof(trans));
0434 trans.tx_buf = ec_dev->dout;
0435 trans.rx_buf = rx_buf;
0436 trans.len = len;
0437 trans.cs_change = 1;
0438 spi_message_add_tail(&trans, &msg);
0439 ret = spi_sync_locked(ec_spi->spi, &msg);
0440
0441
0442 if (!ret) {
0443
0444 for (i = 0; i < len; i++) {
0445 rx_byte = rx_buf[i];
0446
0447
0448
0449
0450
0451
0452
0453
0454
0455
0456
0457
0458
0459
0460
0461 if (rx_byte == EC_SPI_PAST_END ||
0462 rx_byte == EC_SPI_RX_BAD_DATA ||
0463 rx_byte == EC_SPI_NOT_READY) {
0464 ret = -EAGAIN;
0465 break;
0466 }
0467 }
0468 }
0469
0470 if (!ret)
0471 ret = cros_ec_spi_receive_packet(ec_dev,
0472 ec_msg->insize + sizeof(*response));
0473 else if (ret != -EAGAIN)
0474 dev_err(ec_dev->dev, "spi transfer failed: %d\n", ret);
0475
0476 final_ret = terminate_request(ec_dev);
0477
0478 spi_bus_unlock(ec_spi->spi->master);
0479
0480 if (!ret)
0481 ret = final_ret;
0482 if (ret < 0)
0483 goto exit;
0484
0485 ptr = ec_dev->din;
0486
0487
0488 response = (struct ec_host_response *)ptr;
0489 ec_msg->result = response->result;
0490
0491 ret = cros_ec_check_result(ec_dev, ec_msg);
0492 if (ret)
0493 goto exit;
0494
0495 len = response->data_len;
0496 sum = 0;
0497 if (len > ec_msg->insize) {
0498 dev_err(ec_dev->dev, "packet too long (%d bytes, expected %d)",
0499 len, ec_msg->insize);
0500 ret = -EMSGSIZE;
0501 goto exit;
0502 }
0503
0504 for (i = 0; i < sizeof(*response); i++)
0505 sum += ptr[i];
0506
0507
0508 memcpy(ec_msg->data, ptr + sizeof(*response), len);
0509 for (i = 0; i < len; i++)
0510 sum += ec_msg->data[i];
0511
0512 if (sum) {
0513 dev_err(ec_dev->dev,
0514 "bad packet checksum, calculated %x\n",
0515 sum);
0516 ret = -EBADMSG;
0517 goto exit;
0518 }
0519
0520 ret = len;
0521 exit:
0522 kfree(rx_buf);
0523 if (ec_msg->command == EC_CMD_REBOOT_EC)
0524 msleep(EC_REBOOT_DELAY_MS);
0525
0526 return ret;
0527 }
0528
0529
0530
0531
0532
0533
0534
0535 static int do_cros_ec_cmd_xfer_spi(struct cros_ec_device *ec_dev,
0536 struct cros_ec_command *ec_msg)
0537 {
0538 struct cros_ec_spi *ec_spi = ec_dev->priv;
0539 struct spi_transfer trans;
0540 struct spi_message msg;
0541 int i, len;
0542 u8 *ptr;
0543 u8 *rx_buf;
0544 u8 rx_byte;
0545 int sum;
0546 int ret = 0, final_ret;
0547 unsigned long delay;
0548
0549 len = cros_ec_prepare_tx(ec_dev, ec_msg);
0550 if (len < 0)
0551 return len;
0552 dev_dbg(ec_dev->dev, "prepared, len=%d\n", len);
0553
0554
0555 delay = ktime_get_ns() - ec_spi->last_transfer_ns;
0556 if (delay < EC_SPI_RECOVERY_TIME_NS)
0557 ndelay(EC_SPI_RECOVERY_TIME_NS - delay);
0558
0559 rx_buf = kzalloc(len, GFP_KERNEL);
0560 if (!rx_buf)
0561 return -ENOMEM;
0562
0563 spi_bus_lock(ec_spi->spi->master);
0564
0565
0566 debug_packet(ec_dev->dev, "out", ec_dev->dout, len);
0567 memset(&trans, 0, sizeof(trans));
0568 trans.tx_buf = ec_dev->dout;
0569 trans.rx_buf = rx_buf;
0570 trans.len = len;
0571 trans.cs_change = 1;
0572 spi_message_init(&msg);
0573 spi_message_add_tail(&trans, &msg);
0574 ret = spi_sync_locked(ec_spi->spi, &msg);
0575
0576
0577 if (!ret) {
0578
0579 for (i = 0; i < len; i++) {
0580 rx_byte = rx_buf[i];
0581
0582 if (rx_byte == EC_SPI_PAST_END ||
0583 rx_byte == EC_SPI_RX_BAD_DATA ||
0584 rx_byte == EC_SPI_NOT_READY) {
0585 ret = -EAGAIN;
0586 break;
0587 }
0588 }
0589 }
0590
0591 if (!ret)
0592 ret = cros_ec_spi_receive_response(ec_dev,
0593 ec_msg->insize + EC_MSG_TX_PROTO_BYTES);
0594 else if (ret != -EAGAIN)
0595 dev_err(ec_dev->dev, "spi transfer failed: %d\n", ret);
0596
0597 final_ret = terminate_request(ec_dev);
0598
0599 spi_bus_unlock(ec_spi->spi->master);
0600
0601 if (!ret)
0602 ret = final_ret;
0603 if (ret < 0)
0604 goto exit;
0605
0606 ptr = ec_dev->din;
0607
0608
0609 ec_msg->result = ptr[0];
0610 ret = cros_ec_check_result(ec_dev, ec_msg);
0611 if (ret)
0612 goto exit;
0613
0614 len = ptr[1];
0615 sum = ptr[0] + ptr[1];
0616 if (len > ec_msg->insize) {
0617 dev_err(ec_dev->dev, "packet too long (%d bytes, expected %d)",
0618 len, ec_msg->insize);
0619 ret = -ENOSPC;
0620 goto exit;
0621 }
0622
0623
0624 for (i = 0; i < len; i++) {
0625 sum += ptr[i + 2];
0626 if (ec_msg->insize)
0627 ec_msg->data[i] = ptr[i + 2];
0628 }
0629 sum &= 0xff;
0630
0631 debug_packet(ec_dev->dev, "in", ptr, len + 3);
0632
0633 if (sum != ptr[len + 2]) {
0634 dev_err(ec_dev->dev,
0635 "bad packet checksum, expected %02x, got %02x\n",
0636 sum, ptr[len + 2]);
0637 ret = -EBADMSG;
0638 goto exit;
0639 }
0640
0641 ret = len;
0642 exit:
0643 kfree(rx_buf);
0644 if (ec_msg->command == EC_CMD_REBOOT_EC)
0645 msleep(EC_REBOOT_DELAY_MS);
0646
0647 return ret;
0648 }
0649
0650 static void cros_ec_xfer_high_pri_work(struct kthread_work *work)
0651 {
0652 struct cros_ec_xfer_work_params *params;
0653
0654 params = container_of(work, struct cros_ec_xfer_work_params, work);
0655 params->ret = params->fn(params->ec_dev, params->ec_msg);
0656 }
0657
0658 static int cros_ec_xfer_high_pri(struct cros_ec_device *ec_dev,
0659 struct cros_ec_command *ec_msg,
0660 cros_ec_xfer_fn_t fn)
0661 {
0662 struct cros_ec_spi *ec_spi = ec_dev->priv;
0663 struct cros_ec_xfer_work_params params = {
0664 .work = KTHREAD_WORK_INIT(params.work,
0665 cros_ec_xfer_high_pri_work),
0666 .ec_dev = ec_dev,
0667 .ec_msg = ec_msg,
0668 .fn = fn,
0669 };
0670
0671
0672
0673
0674
0675
0676
0677
0678
0679
0680 kthread_queue_work(ec_spi->high_pri_worker, ¶ms.work);
0681 kthread_flush_work(¶ms.work);
0682
0683 return params.ret;
0684 }
0685
0686 static int cros_ec_pkt_xfer_spi(struct cros_ec_device *ec_dev,
0687 struct cros_ec_command *ec_msg)
0688 {
0689 return cros_ec_xfer_high_pri(ec_dev, ec_msg, do_cros_ec_pkt_xfer_spi);
0690 }
0691
0692 static int cros_ec_cmd_xfer_spi(struct cros_ec_device *ec_dev,
0693 struct cros_ec_command *ec_msg)
0694 {
0695 return cros_ec_xfer_high_pri(ec_dev, ec_msg, do_cros_ec_cmd_xfer_spi);
0696 }
0697
0698 static void cros_ec_spi_dt_probe(struct cros_ec_spi *ec_spi, struct device *dev)
0699 {
0700 struct device_node *np = dev->of_node;
0701 u32 val;
0702 int ret;
0703
0704 ret = of_property_read_u32(np, "google,cros-ec-spi-pre-delay", &val);
0705 if (!ret)
0706 ec_spi->start_of_msg_delay = val;
0707
0708 ret = of_property_read_u32(np, "google,cros-ec-spi-msg-delay", &val);
0709 if (!ret)
0710 ec_spi->end_of_msg_delay = val;
0711 }
0712
0713 static void cros_ec_spi_high_pri_release(void *worker)
0714 {
0715 kthread_destroy_worker(worker);
0716 }
0717
0718 static int cros_ec_spi_devm_high_pri_alloc(struct device *dev,
0719 struct cros_ec_spi *ec_spi)
0720 {
0721 int err;
0722
0723 ec_spi->high_pri_worker =
0724 kthread_create_worker(0, "cros_ec_spi_high_pri");
0725
0726 if (IS_ERR(ec_spi->high_pri_worker)) {
0727 err = PTR_ERR(ec_spi->high_pri_worker);
0728 dev_err(dev, "Can't create cros_ec high pri worker: %d\n", err);
0729 return err;
0730 }
0731
0732 err = devm_add_action_or_reset(dev, cros_ec_spi_high_pri_release,
0733 ec_spi->high_pri_worker);
0734 if (err)
0735 return err;
0736
0737 sched_set_fifo(ec_spi->high_pri_worker->task);
0738
0739 return 0;
0740 }
0741
0742 static int cros_ec_spi_probe(struct spi_device *spi)
0743 {
0744 struct device *dev = &spi->dev;
0745 struct cros_ec_device *ec_dev;
0746 struct cros_ec_spi *ec_spi;
0747 int err;
0748
0749 spi->rt = true;
0750 err = spi_setup(spi);
0751 if (err < 0)
0752 return err;
0753
0754 ec_spi = devm_kzalloc(dev, sizeof(*ec_spi), GFP_KERNEL);
0755 if (ec_spi == NULL)
0756 return -ENOMEM;
0757 ec_spi->spi = spi;
0758 ec_dev = devm_kzalloc(dev, sizeof(*ec_dev), GFP_KERNEL);
0759 if (!ec_dev)
0760 return -ENOMEM;
0761
0762
0763 cros_ec_spi_dt_probe(ec_spi, dev);
0764
0765 spi_set_drvdata(spi, ec_dev);
0766 ec_dev->dev = dev;
0767 ec_dev->priv = ec_spi;
0768 ec_dev->irq = spi->irq;
0769 ec_dev->cmd_xfer = cros_ec_cmd_xfer_spi;
0770 ec_dev->pkt_xfer = cros_ec_pkt_xfer_spi;
0771 ec_dev->phys_name = dev_name(&ec_spi->spi->dev);
0772 ec_dev->din_size = EC_MSG_PREAMBLE_COUNT +
0773 sizeof(struct ec_host_response) +
0774 sizeof(struct ec_response_get_protocol_info);
0775 ec_dev->dout_size = sizeof(struct ec_host_request);
0776
0777 ec_spi->last_transfer_ns = ktime_get_ns();
0778
0779 err = cros_ec_spi_devm_high_pri_alloc(dev, ec_spi);
0780 if (err)
0781 return err;
0782
0783 err = cros_ec_register(ec_dev);
0784 if (err) {
0785 dev_err(dev, "cannot register EC\n");
0786 return err;
0787 }
0788
0789 device_init_wakeup(&spi->dev, true);
0790
0791 return 0;
0792 }
0793
0794 static void cros_ec_spi_remove(struct spi_device *spi)
0795 {
0796 struct cros_ec_device *ec_dev = spi_get_drvdata(spi);
0797
0798 cros_ec_unregister(ec_dev);
0799 }
0800
0801 #ifdef CONFIG_PM_SLEEP
0802 static int cros_ec_spi_suspend(struct device *dev)
0803 {
0804 struct cros_ec_device *ec_dev = dev_get_drvdata(dev);
0805
0806 return cros_ec_suspend(ec_dev);
0807 }
0808
0809 static int cros_ec_spi_resume(struct device *dev)
0810 {
0811 struct cros_ec_device *ec_dev = dev_get_drvdata(dev);
0812
0813 return cros_ec_resume(ec_dev);
0814 }
0815 #endif
0816
0817 static SIMPLE_DEV_PM_OPS(cros_ec_spi_pm_ops, cros_ec_spi_suspend,
0818 cros_ec_spi_resume);
0819
0820 static const struct of_device_id cros_ec_spi_of_match[] = {
0821 { .compatible = "google,cros-ec-spi", },
0822 { },
0823 };
0824 MODULE_DEVICE_TABLE(of, cros_ec_spi_of_match);
0825
0826 static const struct spi_device_id cros_ec_spi_id[] = {
0827 { "cros-ec-spi", 0 },
0828 { }
0829 };
0830 MODULE_DEVICE_TABLE(spi, cros_ec_spi_id);
0831
0832 static struct spi_driver cros_ec_driver_spi = {
0833 .driver = {
0834 .name = "cros-ec-spi",
0835 .of_match_table = cros_ec_spi_of_match,
0836 .pm = &cros_ec_spi_pm_ops,
0837 },
0838 .probe = cros_ec_spi_probe,
0839 .remove = cros_ec_spi_remove,
0840 .id_table = cros_ec_spi_id,
0841 };
0842
0843 module_spi_driver(cros_ec_driver_spi);
0844
0845 MODULE_LICENSE("GPL v2");
0846 MODULE_DESCRIPTION("SPI interface for ChromeOS Embedded Controller");