0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014 #include <asm/unaligned.h>
0015 #include <linux/acpi.h>
0016 #include <linux/delay.h>
0017 #include <linux/jiffies.h>
0018 #include <linux/kernel.h>
0019 #include <linux/module.h>
0020 #include <linux/notifier.h>
0021 #include <linux/platform_device.h>
0022 #include <linux/rwsem.h>
0023
0024 #include <linux/surface_aggregator/controller.h>
0025 #include <linux/surface_acpi_notify.h>
0026
0027 struct san_data {
0028 struct device *dev;
0029 struct ssam_controller *ctrl;
0030
0031 struct acpi_connection_info info;
0032
0033 struct ssam_event_notifier nf_bat;
0034 struct ssam_event_notifier nf_tmp;
0035 };
0036
0037 #define to_san_data(ptr, member) \
0038 container_of(ptr, struct san_data, member)
0039
0040 static struct workqueue_struct *san_wq;
0041
0042
0043
0044 struct san_rqsg_if {
0045 struct rw_semaphore lock;
0046 struct device *dev;
0047 struct blocking_notifier_head nh;
0048 };
0049
0050 static struct san_rqsg_if san_rqsg_if = {
0051 .lock = __RWSEM_INITIALIZER(san_rqsg_if.lock),
0052 .dev = NULL,
0053 .nh = BLOCKING_NOTIFIER_INIT(san_rqsg_if.nh),
0054 };
0055
0056 static int san_set_rqsg_interface_device(struct device *dev)
0057 {
0058 int status = 0;
0059
0060 down_write(&san_rqsg_if.lock);
0061 if (!san_rqsg_if.dev && dev)
0062 san_rqsg_if.dev = dev;
0063 else
0064 status = -EBUSY;
0065 up_write(&san_rqsg_if.lock);
0066
0067 return status;
0068 }
0069
0070
0071
0072
0073
0074
0075
0076
0077
0078
0079
0080
0081
0082
0083
0084
0085
0086 int san_client_link(struct device *client)
0087 {
0088 const u32 flags = DL_FLAG_PM_RUNTIME | DL_FLAG_AUTOREMOVE_CONSUMER;
0089 struct device_link *link;
0090
0091 down_read(&san_rqsg_if.lock);
0092
0093 if (!san_rqsg_if.dev) {
0094 up_read(&san_rqsg_if.lock);
0095 return -ENXIO;
0096 }
0097
0098 link = device_link_add(client, san_rqsg_if.dev, flags);
0099 if (!link) {
0100 up_read(&san_rqsg_if.lock);
0101 return -ENOMEM;
0102 }
0103
0104 if (READ_ONCE(link->status) == DL_STATE_SUPPLIER_UNBIND) {
0105 up_read(&san_rqsg_if.lock);
0106 return -ENXIO;
0107 }
0108
0109 up_read(&san_rqsg_if.lock);
0110 return 0;
0111 }
0112 EXPORT_SYMBOL_GPL(san_client_link);
0113
0114
0115
0116
0117
0118
0119
0120
0121
0122 int san_dgpu_notifier_register(struct notifier_block *nb)
0123 {
0124 return blocking_notifier_chain_register(&san_rqsg_if.nh, nb);
0125 }
0126 EXPORT_SYMBOL_GPL(san_dgpu_notifier_register);
0127
0128
0129
0130
0131
0132 int san_dgpu_notifier_unregister(struct notifier_block *nb)
0133 {
0134 return blocking_notifier_chain_unregister(&san_rqsg_if.nh, nb);
0135 }
0136 EXPORT_SYMBOL_GPL(san_dgpu_notifier_unregister);
0137
0138 static int san_dgpu_notifier_call(struct san_dgpu_event *evt)
0139 {
0140 int ret;
0141
0142 ret = blocking_notifier_call_chain(&san_rqsg_if.nh, evt->command, evt);
0143 return notifier_to_errno(ret);
0144 }
0145
0146
0147
0148
0149 #define SAN_DSM_REVISION 0
0150
0151
0152 static const guid_t SAN_DSM_UUID =
0153 GUID_INIT(0x93b666c5, 0x70c6, 0x469f, 0xa2, 0x15, 0x3d,
0154 0x48, 0x7c, 0x91, 0xab, 0x3c);
0155
0156 enum san_dsm_event_fn {
0157 SAN_DSM_EVENT_FN_BAT1_STAT = 0x03,
0158 SAN_DSM_EVENT_FN_BAT1_INFO = 0x04,
0159 SAN_DSM_EVENT_FN_ADP1_STAT = 0x05,
0160 SAN_DSM_EVENT_FN_ADP1_INFO = 0x06,
0161 SAN_DSM_EVENT_FN_BAT2_STAT = 0x07,
0162 SAN_DSM_EVENT_FN_BAT2_INFO = 0x08,
0163 SAN_DSM_EVENT_FN_THERMAL = 0x09,
0164 SAN_DSM_EVENT_FN_DPTF = 0x0a,
0165 };
0166
0167 enum sam_event_cid_bat {
0168 SAM_EVENT_CID_BAT_BIX = 0x15,
0169 SAM_EVENT_CID_BAT_BST = 0x16,
0170 SAM_EVENT_CID_BAT_ADP = 0x17,
0171 SAM_EVENT_CID_BAT_PROT = 0x18,
0172 SAM_EVENT_CID_BAT_DPTF = 0x4f,
0173 };
0174
0175 enum sam_event_cid_tmp {
0176 SAM_EVENT_CID_TMP_TRIP = 0x0b,
0177 };
0178
0179 struct san_event_work {
0180 struct delayed_work work;
0181 struct device *dev;
0182 struct ssam_event event;
0183 };
0184
0185 static int san_acpi_notify_event(struct device *dev, u64 func,
0186 union acpi_object *param)
0187 {
0188 acpi_handle san = ACPI_HANDLE(dev);
0189 union acpi_object *obj;
0190 int status = 0;
0191
0192 if (!acpi_check_dsm(san, &SAN_DSM_UUID, SAN_DSM_REVISION, BIT_ULL(func)))
0193 return 0;
0194
0195 dev_dbg(dev, "notify event %#04llx\n", func);
0196
0197 obj = acpi_evaluate_dsm_typed(san, &SAN_DSM_UUID, SAN_DSM_REVISION,
0198 func, param, ACPI_TYPE_BUFFER);
0199 if (!obj)
0200 return -EFAULT;
0201
0202 if (obj->buffer.length != 1 || obj->buffer.pointer[0] != 0) {
0203 dev_err(dev, "got unexpected result from _DSM\n");
0204 status = -EPROTO;
0205 }
0206
0207 ACPI_FREE(obj);
0208 return status;
0209 }
0210
0211 static int san_evt_bat_adp(struct device *dev, const struct ssam_event *event)
0212 {
0213 int status;
0214
0215 status = san_acpi_notify_event(dev, SAN_DSM_EVENT_FN_ADP1_STAT, NULL);
0216 if (status)
0217 return status;
0218
0219
0220
0221
0222
0223
0224
0225
0226 status = san_acpi_notify_event(dev, SAN_DSM_EVENT_FN_BAT1_STAT, NULL);
0227 if (status)
0228 return status;
0229
0230 return san_acpi_notify_event(dev, SAN_DSM_EVENT_FN_BAT2_STAT, NULL);
0231 }
0232
0233 static int san_evt_bat_bix(struct device *dev, const struct ssam_event *event)
0234 {
0235 enum san_dsm_event_fn fn;
0236
0237 if (event->instance_id == 0x02)
0238 fn = SAN_DSM_EVENT_FN_BAT2_INFO;
0239 else
0240 fn = SAN_DSM_EVENT_FN_BAT1_INFO;
0241
0242 return san_acpi_notify_event(dev, fn, NULL);
0243 }
0244
0245 static int san_evt_bat_bst(struct device *dev, const struct ssam_event *event)
0246 {
0247 enum san_dsm_event_fn fn;
0248
0249 if (event->instance_id == 0x02)
0250 fn = SAN_DSM_EVENT_FN_BAT2_STAT;
0251 else
0252 fn = SAN_DSM_EVENT_FN_BAT1_STAT;
0253
0254 return san_acpi_notify_event(dev, fn, NULL);
0255 }
0256
0257 static int san_evt_bat_dptf(struct device *dev, const struct ssam_event *event)
0258 {
0259 union acpi_object payload;
0260
0261
0262
0263
0264
0265
0266 payload.type = ACPI_TYPE_BUFFER;
0267 payload.buffer.length = event->length;
0268 payload.buffer.pointer = (u8 *)&event->data[0];
0269
0270 return san_acpi_notify_event(dev, SAN_DSM_EVENT_FN_DPTF, &payload);
0271 }
0272
0273 static unsigned long san_evt_bat_delay(u8 cid)
0274 {
0275 switch (cid) {
0276 case SAM_EVENT_CID_BAT_ADP:
0277
0278
0279
0280
0281 return msecs_to_jiffies(5000);
0282
0283 case SAM_EVENT_CID_BAT_BST:
0284
0285 return msecs_to_jiffies(2000);
0286
0287 default:
0288 return 0;
0289 }
0290 }
0291
0292 static bool san_evt_bat(const struct ssam_event *event, struct device *dev)
0293 {
0294 int status;
0295
0296 switch (event->command_id) {
0297 case SAM_EVENT_CID_BAT_BIX:
0298 status = san_evt_bat_bix(dev, event);
0299 break;
0300
0301 case SAM_EVENT_CID_BAT_BST:
0302 status = san_evt_bat_bst(dev, event);
0303 break;
0304
0305 case SAM_EVENT_CID_BAT_ADP:
0306 status = san_evt_bat_adp(dev, event);
0307 break;
0308
0309 case SAM_EVENT_CID_BAT_PROT:
0310
0311
0312
0313
0314 return true;
0315
0316 case SAM_EVENT_CID_BAT_DPTF:
0317 status = san_evt_bat_dptf(dev, event);
0318 break;
0319
0320 default:
0321 return false;
0322 }
0323
0324 if (status) {
0325 dev_err(dev, "error handling power event (cid = %#04x)\n",
0326 event->command_id);
0327 }
0328
0329 return true;
0330 }
0331
0332 static void san_evt_bat_workfn(struct work_struct *work)
0333 {
0334 struct san_event_work *ev;
0335
0336 ev = container_of(work, struct san_event_work, work.work);
0337 san_evt_bat(&ev->event, ev->dev);
0338 kfree(ev);
0339 }
0340
0341 static u32 san_evt_bat_nf(struct ssam_event_notifier *nf,
0342 const struct ssam_event *event)
0343 {
0344 struct san_data *d = to_san_data(nf, nf_bat);
0345 struct san_event_work *work;
0346 unsigned long delay = san_evt_bat_delay(event->command_id);
0347
0348 if (delay == 0)
0349 return san_evt_bat(event, d->dev) ? SSAM_NOTIF_HANDLED : 0;
0350
0351 work = kzalloc(sizeof(*work) + event->length, GFP_KERNEL);
0352 if (!work)
0353 return ssam_notifier_from_errno(-ENOMEM);
0354
0355 INIT_DELAYED_WORK(&work->work, san_evt_bat_workfn);
0356 work->dev = d->dev;
0357
0358 memcpy(&work->event, event, sizeof(struct ssam_event) + event->length);
0359
0360 queue_delayed_work(san_wq, &work->work, delay);
0361 return SSAM_NOTIF_HANDLED;
0362 }
0363
0364 static int san_evt_tmp_trip(struct device *dev, const struct ssam_event *event)
0365 {
0366 union acpi_object param;
0367
0368
0369
0370
0371
0372
0373 param.type = ACPI_TYPE_INTEGER;
0374 param.integer.value = event->instance_id;
0375
0376 return san_acpi_notify_event(dev, SAN_DSM_EVENT_FN_THERMAL, ¶m);
0377 }
0378
0379 static bool san_evt_tmp(const struct ssam_event *event, struct device *dev)
0380 {
0381 int status;
0382
0383 switch (event->command_id) {
0384 case SAM_EVENT_CID_TMP_TRIP:
0385 status = san_evt_tmp_trip(dev, event);
0386 break;
0387
0388 default:
0389 return false;
0390 }
0391
0392 if (status) {
0393 dev_err(dev, "error handling thermal event (cid = %#04x)\n",
0394 event->command_id);
0395 }
0396
0397 return true;
0398 }
0399
0400 static u32 san_evt_tmp_nf(struct ssam_event_notifier *nf,
0401 const struct ssam_event *event)
0402 {
0403 struct san_data *d = to_san_data(nf, nf_tmp);
0404
0405 return san_evt_tmp(event, d->dev) ? SSAM_NOTIF_HANDLED : 0;
0406 }
0407
0408
0409
0410
0411 struct gsb_data_in {
0412 u8 cv;
0413 } __packed;
0414
0415 struct gsb_data_rqsx {
0416 u8 cv;
0417 u8 tc;
0418 u8 tid;
0419 u8 iid;
0420 u8 snc;
0421 u8 cid;
0422 u16 cdl;
0423 u8 pld[];
0424 } __packed;
0425
0426 struct gsb_data_etwl {
0427 u8 cv;
0428 u8 etw3;
0429 u8 etw4;
0430 u8 msg[];
0431 } __packed;
0432
0433 struct gsb_data_out {
0434 u8 status;
0435 u8 len;
0436 u8 pld[];
0437 } __packed;
0438
0439 union gsb_buffer_data {
0440 struct gsb_data_in in;
0441 struct gsb_data_rqsx rqsx;
0442 struct gsb_data_etwl etwl;
0443 struct gsb_data_out out;
0444 };
0445
0446 struct gsb_buffer {
0447 u8 status;
0448 u8 len;
0449 union gsb_buffer_data data;
0450 } __packed;
0451
0452 #define SAN_GSB_MAX_RQSX_PAYLOAD (U8_MAX - 2 - sizeof(struct gsb_data_rqsx))
0453 #define SAN_GSB_MAX_RESPONSE (U8_MAX - 2 - sizeof(struct gsb_data_out))
0454
0455 #define SAN_GSB_COMMAND 0
0456
0457 enum san_gsb_request_cv {
0458 SAN_GSB_REQUEST_CV_RQST = 0x01,
0459 SAN_GSB_REQUEST_CV_ETWL = 0x02,
0460 SAN_GSB_REQUEST_CV_RQSG = 0x03,
0461 };
0462
0463 #define SAN_REQUEST_NUM_TRIES 5
0464
0465 static acpi_status san_etwl(struct san_data *d, struct gsb_buffer *b)
0466 {
0467 struct gsb_data_etwl *etwl = &b->data.etwl;
0468
0469 if (b->len < sizeof(struct gsb_data_etwl)) {
0470 dev_err(d->dev, "invalid ETWL package (len = %d)\n", b->len);
0471 return AE_OK;
0472 }
0473
0474 dev_err(d->dev, "ETWL(%#04x, %#04x): %.*s\n", etwl->etw3, etwl->etw4,
0475 (unsigned int)(b->len - sizeof(struct gsb_data_etwl)),
0476 (char *)etwl->msg);
0477
0478
0479 b->status = 0x00;
0480 b->len = 0x00;
0481
0482 return AE_OK;
0483 }
0484
0485 static
0486 struct gsb_data_rqsx *san_validate_rqsx(struct device *dev, const char *type,
0487 struct gsb_buffer *b)
0488 {
0489 struct gsb_data_rqsx *rqsx = &b->data.rqsx;
0490
0491 if (b->len < sizeof(struct gsb_data_rqsx)) {
0492 dev_err(dev, "invalid %s package (len = %d)\n", type, b->len);
0493 return NULL;
0494 }
0495
0496 if (get_unaligned(&rqsx->cdl) != b->len - sizeof(struct gsb_data_rqsx)) {
0497 dev_err(dev, "bogus %s package (len = %d, cdl = %d)\n",
0498 type, b->len, get_unaligned(&rqsx->cdl));
0499 return NULL;
0500 }
0501
0502 if (get_unaligned(&rqsx->cdl) > SAN_GSB_MAX_RQSX_PAYLOAD) {
0503 dev_err(dev, "payload for %s package too large (cdl = %d)\n",
0504 type, get_unaligned(&rqsx->cdl));
0505 return NULL;
0506 }
0507
0508 return rqsx;
0509 }
0510
0511 static void gsb_rqsx_response_error(struct gsb_buffer *gsb, int status)
0512 {
0513 gsb->status = 0x00;
0514 gsb->len = 0x02;
0515 gsb->data.out.status = (u8)(-status);
0516 gsb->data.out.len = 0x00;
0517 }
0518
0519 static void gsb_rqsx_response_success(struct gsb_buffer *gsb, u8 *ptr, size_t len)
0520 {
0521 gsb->status = 0x00;
0522 gsb->len = len + 2;
0523 gsb->data.out.status = 0x00;
0524 gsb->data.out.len = len;
0525
0526 if (len)
0527 memcpy(&gsb->data.out.pld[0], ptr, len);
0528 }
0529
0530 static acpi_status san_rqst_fixup_suspended(struct san_data *d,
0531 struct ssam_request *rqst,
0532 struct gsb_buffer *gsb)
0533 {
0534 if (rqst->target_category == SSAM_SSH_TC_BAS && rqst->command_id == 0x0D) {
0535 u8 base_state = 1;
0536
0537
0538
0539
0540
0541
0542
0543
0544
0545
0546
0547
0548
0549
0550
0551
0552 dev_dbg(d->dev, "rqst: fixup: base-state quirk\n");
0553
0554 gsb_rqsx_response_success(gsb, &base_state, sizeof(base_state));
0555 return AE_OK;
0556 }
0557
0558 gsb_rqsx_response_error(gsb, -ENXIO);
0559 return AE_OK;
0560 }
0561
0562 static acpi_status san_rqst(struct san_data *d, struct gsb_buffer *buffer)
0563 {
0564 u8 rspbuf[SAN_GSB_MAX_RESPONSE];
0565 struct gsb_data_rqsx *gsb_rqst;
0566 struct ssam_request rqst;
0567 struct ssam_response rsp;
0568 int status = 0;
0569
0570 gsb_rqst = san_validate_rqsx(d->dev, "RQST", buffer);
0571 if (!gsb_rqst)
0572 return AE_OK;
0573
0574 rqst.target_category = gsb_rqst->tc;
0575 rqst.target_id = gsb_rqst->tid;
0576 rqst.command_id = gsb_rqst->cid;
0577 rqst.instance_id = gsb_rqst->iid;
0578 rqst.flags = gsb_rqst->snc ? SSAM_REQUEST_HAS_RESPONSE : 0;
0579 rqst.length = get_unaligned(&gsb_rqst->cdl);
0580 rqst.payload = &gsb_rqst->pld[0];
0581
0582 rsp.capacity = ARRAY_SIZE(rspbuf);
0583 rsp.length = 0;
0584 rsp.pointer = &rspbuf[0];
0585
0586
0587 if (d->dev->power.is_suspended) {
0588 dev_warn(d->dev, "rqst: device is suspended, not executing\n");
0589 return san_rqst_fixup_suspended(d, &rqst, buffer);
0590 }
0591
0592 status = __ssam_retry(ssam_request_sync_onstack, SAN_REQUEST_NUM_TRIES,
0593 d->ctrl, &rqst, &rsp, SAN_GSB_MAX_RQSX_PAYLOAD);
0594
0595 if (!status) {
0596 gsb_rqsx_response_success(buffer, rsp.pointer, rsp.length);
0597 } else {
0598 dev_err(d->dev, "rqst: failed with error %d\n", status);
0599 gsb_rqsx_response_error(buffer, status);
0600 }
0601
0602 return AE_OK;
0603 }
0604
0605 static acpi_status san_rqsg(struct san_data *d, struct gsb_buffer *buffer)
0606 {
0607 struct gsb_data_rqsx *gsb_rqsg;
0608 struct san_dgpu_event evt;
0609 int status;
0610
0611 gsb_rqsg = san_validate_rqsx(d->dev, "RQSG", buffer);
0612 if (!gsb_rqsg)
0613 return AE_OK;
0614
0615 evt.category = gsb_rqsg->tc;
0616 evt.target = gsb_rqsg->tid;
0617 evt.command = gsb_rqsg->cid;
0618 evt.instance = gsb_rqsg->iid;
0619 evt.length = get_unaligned(&gsb_rqsg->cdl);
0620 evt.payload = &gsb_rqsg->pld[0];
0621
0622 status = san_dgpu_notifier_call(&evt);
0623 if (!status) {
0624 gsb_rqsx_response_success(buffer, NULL, 0);
0625 } else {
0626 dev_err(d->dev, "rqsg: failed with error %d\n", status);
0627 gsb_rqsx_response_error(buffer, status);
0628 }
0629
0630 return AE_OK;
0631 }
0632
0633 static acpi_status san_opreg_handler(u32 function, acpi_physical_address command,
0634 u32 bits, u64 *value64, void *opreg_context,
0635 void *region_context)
0636 {
0637 struct san_data *d = to_san_data(opreg_context, info);
0638 struct gsb_buffer *buffer = (struct gsb_buffer *)value64;
0639 int accessor_type = (function & 0xFFFF0000) >> 16;
0640
0641 if (command != SAN_GSB_COMMAND) {
0642 dev_warn(d->dev, "unsupported command: %#04llx\n", command);
0643 return AE_OK;
0644 }
0645
0646 if (accessor_type != ACPI_GSB_ACCESS_ATTRIB_RAW_PROCESS) {
0647 dev_err(d->dev, "invalid access type: %#04x\n", accessor_type);
0648 return AE_OK;
0649 }
0650
0651
0652 if (buffer->len == 0) {
0653 dev_err(d->dev, "request-package too small\n");
0654 return AE_OK;
0655 }
0656
0657 switch (buffer->data.in.cv) {
0658 case SAN_GSB_REQUEST_CV_RQST:
0659 return san_rqst(d, buffer);
0660
0661 case SAN_GSB_REQUEST_CV_ETWL:
0662 return san_etwl(d, buffer);
0663
0664 case SAN_GSB_REQUEST_CV_RQSG:
0665 return san_rqsg(d, buffer);
0666
0667 default:
0668 dev_warn(d->dev, "unsupported SAN0 request (cv: %#04x)\n",
0669 buffer->data.in.cv);
0670 return AE_OK;
0671 }
0672 }
0673
0674
0675
0676
0677 static int san_events_register(struct platform_device *pdev)
0678 {
0679 struct san_data *d = platform_get_drvdata(pdev);
0680 int status;
0681
0682 d->nf_bat.base.priority = 1;
0683 d->nf_bat.base.fn = san_evt_bat_nf;
0684 d->nf_bat.event.reg = SSAM_EVENT_REGISTRY_SAM;
0685 d->nf_bat.event.id.target_category = SSAM_SSH_TC_BAT;
0686 d->nf_bat.event.id.instance = 0;
0687 d->nf_bat.event.mask = SSAM_EVENT_MASK_TARGET;
0688 d->nf_bat.event.flags = SSAM_EVENT_SEQUENCED;
0689
0690 d->nf_tmp.base.priority = 1;
0691 d->nf_tmp.base.fn = san_evt_tmp_nf;
0692 d->nf_tmp.event.reg = SSAM_EVENT_REGISTRY_SAM;
0693 d->nf_tmp.event.id.target_category = SSAM_SSH_TC_TMP;
0694 d->nf_tmp.event.id.instance = 0;
0695 d->nf_tmp.event.mask = SSAM_EVENT_MASK_TARGET;
0696 d->nf_tmp.event.flags = SSAM_EVENT_SEQUENCED;
0697
0698 status = ssam_notifier_register(d->ctrl, &d->nf_bat);
0699 if (status)
0700 return status;
0701
0702 status = ssam_notifier_register(d->ctrl, &d->nf_tmp);
0703 if (status)
0704 ssam_notifier_unregister(d->ctrl, &d->nf_bat);
0705
0706 return status;
0707 }
0708
0709 static void san_events_unregister(struct platform_device *pdev)
0710 {
0711 struct san_data *d = platform_get_drvdata(pdev);
0712
0713 ssam_notifier_unregister(d->ctrl, &d->nf_bat);
0714 ssam_notifier_unregister(d->ctrl, &d->nf_tmp);
0715 }
0716
0717 #define san_consumer_printk(level, dev, handle, fmt, ...) \
0718 do { \
0719 char *path = "<error getting consumer path>"; \
0720 struct acpi_buffer buffer = { \
0721 .length = ACPI_ALLOCATE_BUFFER, \
0722 .pointer = NULL, \
0723 }; \
0724 \
0725 if (ACPI_SUCCESS(acpi_get_name(handle, ACPI_FULL_PATHNAME, &buffer))) \
0726 path = buffer.pointer; \
0727 \
0728 dev_##level(dev, "[%s]: " fmt, path, ##__VA_ARGS__); \
0729 kfree(buffer.pointer); \
0730 } while (0)
0731
0732 #define san_consumer_dbg(dev, handle, fmt, ...) \
0733 san_consumer_printk(dbg, dev, handle, fmt, ##__VA_ARGS__)
0734
0735 #define san_consumer_warn(dev, handle, fmt, ...) \
0736 san_consumer_printk(warn, dev, handle, fmt, ##__VA_ARGS__)
0737
0738 static bool is_san_consumer(struct platform_device *pdev, acpi_handle handle)
0739 {
0740 struct acpi_handle_list dep_devices;
0741 acpi_handle supplier = ACPI_HANDLE(&pdev->dev);
0742 acpi_status status;
0743 int i;
0744
0745 if (!acpi_has_method(handle, "_DEP"))
0746 return false;
0747
0748 status = acpi_evaluate_reference(handle, "_DEP", NULL, &dep_devices);
0749 if (ACPI_FAILURE(status)) {
0750 san_consumer_dbg(&pdev->dev, handle, "failed to evaluate _DEP\n");
0751 return false;
0752 }
0753
0754 for (i = 0; i < dep_devices.count; i++) {
0755 if (dep_devices.handles[i] == supplier)
0756 return true;
0757 }
0758
0759 return false;
0760 }
0761
0762 static acpi_status san_consumer_setup(acpi_handle handle, u32 lvl,
0763 void *context, void **rv)
0764 {
0765 const u32 flags = DL_FLAG_PM_RUNTIME | DL_FLAG_AUTOREMOVE_SUPPLIER;
0766 struct platform_device *pdev = context;
0767 struct acpi_device *adev;
0768 struct device_link *link;
0769
0770 if (!is_san_consumer(pdev, handle))
0771 return AE_OK;
0772
0773
0774 adev = acpi_fetch_acpi_dev(handle);
0775 if (!adev)
0776 return AE_OK;
0777
0778 san_consumer_dbg(&pdev->dev, handle, "creating device link\n");
0779
0780
0781 link = device_link_add(&adev->dev, &pdev->dev, flags);
0782 if (!link) {
0783 san_consumer_warn(&pdev->dev, handle, "failed to create device link\n");
0784 return AE_OK;
0785 }
0786
0787 return AE_OK;
0788 }
0789
0790 static int san_consumer_links_setup(struct platform_device *pdev)
0791 {
0792 acpi_status status;
0793
0794 status = acpi_walk_namespace(ACPI_TYPE_DEVICE, ACPI_ROOT_OBJECT,
0795 ACPI_UINT32_MAX, san_consumer_setup, NULL,
0796 pdev, NULL);
0797
0798 return status ? -EFAULT : 0;
0799 }
0800
0801 static int san_probe(struct platform_device *pdev)
0802 {
0803 struct acpi_device *san = ACPI_COMPANION(&pdev->dev);
0804 struct ssam_controller *ctrl;
0805 struct san_data *data;
0806 acpi_status astatus;
0807 int status;
0808
0809 ctrl = ssam_client_bind(&pdev->dev);
0810 if (IS_ERR(ctrl))
0811 return PTR_ERR(ctrl) == -ENODEV ? -EPROBE_DEFER : PTR_ERR(ctrl);
0812
0813 status = san_consumer_links_setup(pdev);
0814 if (status)
0815 return status;
0816
0817 data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL);
0818 if (!data)
0819 return -ENOMEM;
0820
0821 data->dev = &pdev->dev;
0822 data->ctrl = ctrl;
0823
0824 platform_set_drvdata(pdev, data);
0825
0826 astatus = acpi_install_address_space_handler(san->handle,
0827 ACPI_ADR_SPACE_GSBUS,
0828 &san_opreg_handler, NULL,
0829 &data->info);
0830 if (ACPI_FAILURE(astatus))
0831 return -ENXIO;
0832
0833 status = san_events_register(pdev);
0834 if (status)
0835 goto err_enable_events;
0836
0837 status = san_set_rqsg_interface_device(&pdev->dev);
0838 if (status)
0839 goto err_install_dev;
0840
0841 acpi_dev_clear_dependencies(san);
0842 return 0;
0843
0844 err_install_dev:
0845 san_events_unregister(pdev);
0846 err_enable_events:
0847 acpi_remove_address_space_handler(san, ACPI_ADR_SPACE_GSBUS,
0848 &san_opreg_handler);
0849 return status;
0850 }
0851
0852 static int san_remove(struct platform_device *pdev)
0853 {
0854 acpi_handle san = ACPI_HANDLE(&pdev->dev);
0855
0856 san_set_rqsg_interface_device(NULL);
0857 acpi_remove_address_space_handler(san, ACPI_ADR_SPACE_GSBUS,
0858 &san_opreg_handler);
0859 san_events_unregister(pdev);
0860
0861
0862
0863
0864
0865 flush_workqueue(san_wq);
0866
0867 return 0;
0868 }
0869
0870 static const struct acpi_device_id san_match[] = {
0871 { "MSHW0091" },
0872 { },
0873 };
0874 MODULE_DEVICE_TABLE(acpi, san_match);
0875
0876 static struct platform_driver surface_acpi_notify = {
0877 .probe = san_probe,
0878 .remove = san_remove,
0879 .driver = {
0880 .name = "surface_acpi_notify",
0881 .acpi_match_table = san_match,
0882 .probe_type = PROBE_PREFER_ASYNCHRONOUS,
0883 },
0884 };
0885
0886 static int __init san_init(void)
0887 {
0888 int ret;
0889
0890 san_wq = alloc_workqueue("san_wq", 0, 0);
0891 if (!san_wq)
0892 return -ENOMEM;
0893 ret = platform_driver_register(&surface_acpi_notify);
0894 if (ret)
0895 destroy_workqueue(san_wq);
0896 return ret;
0897 }
0898 module_init(san_init);
0899
0900 static void __exit san_exit(void)
0901 {
0902 platform_driver_unregister(&surface_acpi_notify);
0903 destroy_workqueue(san_wq);
0904 }
0905 module_exit(san_exit);
0906
0907 MODULE_AUTHOR("Maximilian Luz <luzmaximilian@gmail.com>");
0908 MODULE_DESCRIPTION("Surface ACPI Notify driver for Surface System Aggregator Module");
0909 MODULE_LICENSE("GPL");