1 /* 2 * Copyright (c) 2015, Linaro Limited 3 * 4 * This software is licensed under the terms of the GNU General Public 5 * License version 2, as published by the Free Software Foundation, and 6 * may be copied, distributed, and modified under those terms. 7 * 8 * This program is distributed in the hope that it will be useful, 9 * but WITHOUT ANY WARRANTY; without even the implied warranty of 10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 11 * GNU General Public License for more details. 12 * 13 */ 14 15 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt 16 17 #include <linux/arm-smccc.h> 18 #include <linux/errno.h> 19 #include <linux/io.h> 20 #include <linux/module.h> 21 #include <linux/of.h> 22 #include <linux/of_platform.h> 23 #include <linux/platform_device.h> 24 #include <linux/slab.h> 25 #include <linux/string.h> 26 #include <linux/tee_drv.h> 27 #include <linux/types.h> 28 #include <linux/uaccess.h> 29 #include "optee_private.h" 30 #include "optee_smc.h" 31 #include "shm_pool.h" 32 33 #define DRIVER_NAME "optee" 34 35 #define OPTEE_SHM_NUM_PRIV_PAGES 1 36 37 /** 38 * optee_from_msg_param() - convert from OPTEE_MSG parameters to 39 * struct tee_param 40 * @params: subsystem internal parameter representation 41 * @num_params: number of elements in the parameter arrays 42 * @msg_params: OPTEE_MSG parameters 43 * Returns 0 on success or <0 on failure 44 */ 45 int optee_from_msg_param(struct tee_param *params, size_t num_params, 46 const struct optee_msg_param *msg_params) 47 { 48 int rc; 49 size_t n; 50 struct tee_shm *shm; 51 phys_addr_t pa; 52 53 for (n = 0; n < num_params; n++) { 54 struct tee_param *p = params + n; 55 const struct optee_msg_param *mp = msg_params + n; 56 u32 attr = mp->attr & OPTEE_MSG_ATTR_TYPE_MASK; 57 58 switch (attr) { 59 case OPTEE_MSG_ATTR_TYPE_NONE: 60 p->attr = TEE_IOCTL_PARAM_ATTR_TYPE_NONE; 61 memset(&p->u, 0, sizeof(p->u)); 62 break; 63 case OPTEE_MSG_ATTR_TYPE_VALUE_INPUT: 64 case OPTEE_MSG_ATTR_TYPE_VALUE_OUTPUT: 65 case OPTEE_MSG_ATTR_TYPE_VALUE_INOUT: 66 p->attr = TEE_IOCTL_PARAM_ATTR_TYPE_VALUE_INPUT + 67 attr - OPTEE_MSG_ATTR_TYPE_VALUE_INPUT; 68 p->u.value.a = mp->u.value.a; 69 p->u.value.b = mp->u.value.b; 70 p->u.value.c = mp->u.value.c; 71 break; 72 case OPTEE_MSG_ATTR_TYPE_TMEM_INPUT: 73 case OPTEE_MSG_ATTR_TYPE_TMEM_OUTPUT: 74 case OPTEE_MSG_ATTR_TYPE_TMEM_INOUT: 75 p->attr = TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_INPUT + 76 attr - OPTEE_MSG_ATTR_TYPE_TMEM_INPUT; 77 p->u.memref.size = mp->u.tmem.size; 78 shm = (struct tee_shm *)(unsigned long) 79 mp->u.tmem.shm_ref; 80 if (!shm) { 81 p->u.memref.shm_offs = 0; 82 p->u.memref.shm = NULL; 83 break; 84 } 85 rc = tee_shm_get_pa(shm, 0, &pa); 86 if (rc) 87 return rc; 88 p->u.memref.shm_offs = mp->u.tmem.buf_ptr - pa; 89 p->u.memref.shm = shm; 90 91 /* Check that the memref is covered by the shm object */ 92 if (p->u.memref.size) { 93 size_t o = p->u.memref.shm_offs + 94 p->u.memref.size - 1; 95 96 rc = tee_shm_get_pa(shm, o, NULL); 97 if (rc) 98 return rc; 99 } 100 break; 101 case OPTEE_MSG_ATTR_TYPE_RMEM_INPUT: 102 case OPTEE_MSG_ATTR_TYPE_RMEM_OUTPUT: 103 case OPTEE_MSG_ATTR_TYPE_RMEM_INOUT: 104 p->attr = TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_INPUT + 105 attr - OPTEE_MSG_ATTR_TYPE_RMEM_INPUT; 106 p->u.memref.size = mp->u.rmem.size; 107 shm = (struct tee_shm *)(unsigned long) 108 mp->u.rmem.shm_ref; 109 110 if (!shm) { 111 p->u.memref.shm_offs = 0; 112 p->u.memref.shm = NULL; 113 break; 114 } 115 p->u.memref.shm_offs = mp->u.rmem.offs; 116 p->u.memref.shm = shm; 117 118 break; 119 120 default: 121 return -EINVAL; 122 } 123 } 124 return 0; 125 } 126 127 static int to_msg_param_tmp_mem(struct optee_msg_param *mp, 128 const struct tee_param *p) 129 { 130 int rc; 131 phys_addr_t pa; 132 133 mp->attr = OPTEE_MSG_ATTR_TYPE_TMEM_INPUT + p->attr - 134 TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_INPUT; 135 136 mp->u.tmem.shm_ref = (unsigned long)p->u.memref.shm; 137 mp->u.tmem.size = p->u.memref.size; 138 139 if (!p->u.memref.shm) { 140 mp->u.tmem.buf_ptr = 0; 141 return 0; 142 } 143 144 rc = tee_shm_get_pa(p->u.memref.shm, p->u.memref.shm_offs, &pa); 145 if (rc) 146 return rc; 147 148 mp->u.tmem.buf_ptr = pa; 149 mp->attr |= OPTEE_MSG_ATTR_CACHE_PREDEFINED << 150 OPTEE_MSG_ATTR_CACHE_SHIFT; 151 152 return 0; 153 } 154 155 static int to_msg_param_reg_mem(struct optee_msg_param *mp, 156 const struct tee_param *p) 157 { 158 mp->attr = OPTEE_MSG_ATTR_TYPE_RMEM_INPUT + p->attr - 159 TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_INPUT; 160 161 mp->u.rmem.shm_ref = (unsigned long)p->u.memref.shm; 162 mp->u.rmem.size = p->u.memref.size; 163 mp->u.rmem.offs = p->u.memref.shm_offs; 164 return 0; 165 } 166 167 /** 168 * optee_to_msg_param() - convert from struct tee_params to OPTEE_MSG parameters 169 * @msg_params: OPTEE_MSG parameters 170 * @num_params: number of elements in the parameter arrays 171 * @params: subsystem itnernal parameter representation 172 * Returns 0 on success or <0 on failure 173 */ 174 int optee_to_msg_param(struct optee_msg_param *msg_params, size_t num_params, 175 const struct tee_param *params) 176 { 177 int rc; 178 size_t n; 179 180 for (n = 0; n < num_params; n++) { 181 const struct tee_param *p = params + n; 182 struct optee_msg_param *mp = msg_params + n; 183 184 switch (p->attr) { 185 case TEE_IOCTL_PARAM_ATTR_TYPE_NONE: 186 mp->attr = TEE_IOCTL_PARAM_ATTR_TYPE_NONE; 187 memset(&mp->u, 0, sizeof(mp->u)); 188 break; 189 case TEE_IOCTL_PARAM_ATTR_TYPE_VALUE_INPUT: 190 case TEE_IOCTL_PARAM_ATTR_TYPE_VALUE_OUTPUT: 191 case TEE_IOCTL_PARAM_ATTR_TYPE_VALUE_INOUT: 192 mp->attr = OPTEE_MSG_ATTR_TYPE_VALUE_INPUT + p->attr - 193 TEE_IOCTL_PARAM_ATTR_TYPE_VALUE_INPUT; 194 mp->u.value.a = p->u.value.a; 195 mp->u.value.b = p->u.value.b; 196 mp->u.value.c = p->u.value.c; 197 break; 198 case TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_INPUT: 199 case TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_OUTPUT: 200 case TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_INOUT: 201 if (tee_shm_is_registered(p->u.memref.shm)) 202 rc = to_msg_param_reg_mem(mp, p); 203 else 204 rc = to_msg_param_tmp_mem(mp, p); 205 if (rc) 206 return rc; 207 break; 208 default: 209 return -EINVAL; 210 } 211 } 212 return 0; 213 } 214 215 static void optee_get_version(struct tee_device *teedev, 216 struct tee_ioctl_version_data *vers) 217 { 218 struct tee_ioctl_version_data v = { 219 .impl_id = TEE_IMPL_ID_OPTEE, 220 .impl_caps = TEE_OPTEE_CAP_TZ, 221 .gen_caps = TEE_GEN_CAP_GP, 222 }; 223 struct optee *optee = tee_get_drvdata(teedev); 224 225 if (optee->sec_caps & OPTEE_SMC_SEC_CAP_DYNAMIC_SHM) 226 v.gen_caps |= TEE_GEN_CAP_REG_MEM; 227 *vers = v; 228 } 229 230 static int optee_open(struct tee_context *ctx) 231 { 232 struct optee_context_data *ctxdata; 233 struct tee_device *teedev = ctx->teedev; 234 struct optee *optee = tee_get_drvdata(teedev); 235 236 ctxdata = kzalloc(sizeof(*ctxdata), GFP_KERNEL); 237 if (!ctxdata) 238 return -ENOMEM; 239 240 if (teedev == optee->supp_teedev) { 241 bool busy = true; 242 243 mutex_lock(&optee->supp.mutex); 244 if (!optee->supp.ctx) { 245 busy = false; 246 optee->supp.ctx = ctx; 247 } 248 mutex_unlock(&optee->supp.mutex); 249 if (busy) { 250 kfree(ctxdata); 251 return -EBUSY; 252 } 253 } 254 255 mutex_init(&ctxdata->mutex); 256 INIT_LIST_HEAD(&ctxdata->sess_list); 257 258 ctx->data = ctxdata; 259 return 0; 260 } 261 262 static void optee_release(struct tee_context *ctx) 263 { 264 struct optee_context_data *ctxdata = ctx->data; 265 struct tee_device *teedev = ctx->teedev; 266 struct optee *optee = tee_get_drvdata(teedev); 267 struct tee_shm *shm; 268 struct optee_msg_arg *arg = NULL; 269 phys_addr_t parg; 270 struct optee_session *sess; 271 struct optee_session *sess_tmp; 272 273 if (!ctxdata) 274 return; 275 276 shm = tee_shm_alloc(ctx, sizeof(struct optee_msg_arg), TEE_SHM_MAPPED); 277 if (!IS_ERR(shm)) { 278 arg = tee_shm_get_va(shm, 0); 279 /* 280 * If va2pa fails for some reason, we can't call into 281 * secure world, only free the memory. Secure OS will leak 282 * sessions and finally refuse more sessions, but we will 283 * at least let normal world reclaim its memory. 284 */ 285 if (!IS_ERR(arg)) 286 if (tee_shm_va2pa(shm, arg, &parg)) 287 arg = NULL; /* prevent usage of parg below */ 288 } 289 290 list_for_each_entry_safe(sess, sess_tmp, &ctxdata->sess_list, 291 list_node) { 292 list_del(&sess->list_node); 293 if (!IS_ERR_OR_NULL(arg)) { 294 memset(arg, 0, sizeof(*arg)); 295 arg->cmd = OPTEE_MSG_CMD_CLOSE_SESSION; 296 arg->session = sess->session_id; 297 optee_do_call_with_arg(ctx, parg); 298 } 299 kfree(sess); 300 } 301 kfree(ctxdata); 302 303 if (!IS_ERR(shm)) 304 tee_shm_free(shm); 305 306 ctx->data = NULL; 307 308 if (teedev == optee->supp_teedev) 309 optee_supp_release(&optee->supp); 310 } 311 312 static const struct tee_driver_ops optee_ops = { 313 .get_version = optee_get_version, 314 .open = optee_open, 315 .release = optee_release, 316 .open_session = optee_open_session, 317 .close_session = optee_close_session, 318 .invoke_func = optee_invoke_func, 319 .cancel_req = optee_cancel_req, 320 .shm_register = optee_shm_register, 321 .shm_unregister = optee_shm_unregister, 322 }; 323 324 static const struct tee_desc optee_desc = { 325 .name = DRIVER_NAME "-clnt", 326 .ops = &optee_ops, 327 .owner = THIS_MODULE, 328 }; 329 330 static const struct tee_driver_ops optee_supp_ops = { 331 .get_version = optee_get_version, 332 .open = optee_open, 333 .release = optee_release, 334 .supp_recv = optee_supp_recv, 335 .supp_send = optee_supp_send, 336 .shm_register = optee_shm_register_supp, 337 .shm_unregister = optee_shm_unregister_supp, 338 }; 339 340 static const struct tee_desc optee_supp_desc = { 341 .name = DRIVER_NAME "-supp", 342 .ops = &optee_supp_ops, 343 .owner = THIS_MODULE, 344 .flags = TEE_DESC_PRIVILEGED, 345 }; 346 347 static bool optee_msg_api_uid_is_optee_api(optee_invoke_fn *invoke_fn) 348 { 349 struct arm_smccc_res res; 350 351 invoke_fn(OPTEE_SMC_CALLS_UID, 0, 0, 0, 0, 0, 0, 0, &res); 352 353 if (res.a0 == OPTEE_MSG_UID_0 && res.a1 == OPTEE_MSG_UID_1 && 354 res.a2 == OPTEE_MSG_UID_2 && res.a3 == OPTEE_MSG_UID_3) 355 return true; 356 return false; 357 } 358 359 static bool optee_msg_api_revision_is_compatible(optee_invoke_fn *invoke_fn) 360 { 361 union { 362 struct arm_smccc_res smccc; 363 struct optee_smc_calls_revision_result result; 364 } res; 365 366 invoke_fn(OPTEE_SMC_CALLS_REVISION, 0, 0, 0, 0, 0, 0, 0, &res.smccc); 367 368 if (res.result.major == OPTEE_MSG_REVISION_MAJOR && 369 (int)res.result.minor >= OPTEE_MSG_REVISION_MINOR) 370 return true; 371 return false; 372 } 373 374 static bool optee_msg_exchange_capabilities(optee_invoke_fn *invoke_fn, 375 u32 *sec_caps) 376 { 377 union { 378 struct arm_smccc_res smccc; 379 struct optee_smc_exchange_capabilities_result result; 380 } res; 381 u32 a1 = 0; 382 383 /* 384 * TODO This isn't enough to tell if it's UP system (from kernel 385 * point of view) or not, is_smp() returns the the information 386 * needed, but can't be called directly from here. 387 */ 388 if (!IS_ENABLED(CONFIG_SMP) || nr_cpu_ids == 1) 389 a1 |= OPTEE_SMC_NSEC_CAP_UNIPROCESSOR; 390 391 invoke_fn(OPTEE_SMC_EXCHANGE_CAPABILITIES, a1, 0, 0, 0, 0, 0, 0, 392 &res.smccc); 393 394 if (res.result.status != OPTEE_SMC_RETURN_OK) 395 return false; 396 397 *sec_caps = res.result.capabilities; 398 return true; 399 } 400 401 static struct tee_shm_pool * 402 optee_config_shm_memremap(optee_invoke_fn *invoke_fn, void **memremaped_shm, 403 u32 sec_caps) 404 { 405 union { 406 struct arm_smccc_res smccc; 407 struct optee_smc_get_shm_config_result result; 408 } res; 409 unsigned long vaddr; 410 phys_addr_t paddr; 411 size_t size; 412 phys_addr_t begin; 413 phys_addr_t end; 414 void *va; 415 struct tee_shm_pool_mgr *priv_mgr; 416 struct tee_shm_pool_mgr *dmabuf_mgr; 417 void *rc; 418 419 invoke_fn(OPTEE_SMC_GET_SHM_CONFIG, 0, 0, 0, 0, 0, 0, 0, &res.smccc); 420 if (res.result.status != OPTEE_SMC_RETURN_OK) { 421 pr_info("shm service not available\n"); 422 return ERR_PTR(-ENOENT); 423 } 424 425 if (res.result.settings != OPTEE_SMC_SHM_CACHED) { 426 pr_err("only normal cached shared memory supported\n"); 427 return ERR_PTR(-EINVAL); 428 } 429 430 begin = roundup(res.result.start, PAGE_SIZE); 431 end = rounddown(res.result.start + res.result.size, PAGE_SIZE); 432 paddr = begin; 433 size = end - begin; 434 435 if (size < 2 * OPTEE_SHM_NUM_PRIV_PAGES * PAGE_SIZE) { 436 pr_err("too small shared memory area\n"); 437 return ERR_PTR(-EINVAL); 438 } 439 440 va = memremap(paddr, size, MEMREMAP_WB); 441 if (!va) { 442 pr_err("shared memory ioremap failed\n"); 443 return ERR_PTR(-EINVAL); 444 } 445 vaddr = (unsigned long)va; 446 447 /* 448 * If OP-TEE can work with unregistered SHM, we will use own pool 449 * for private shm 450 */ 451 if (sec_caps & OPTEE_SMC_SEC_CAP_DYNAMIC_SHM) { 452 rc = optee_shm_pool_alloc_pages(); 453 if (IS_ERR(rc)) 454 goto err_memunmap; 455 priv_mgr = rc; 456 } else { 457 const size_t sz = OPTEE_SHM_NUM_PRIV_PAGES * PAGE_SIZE; 458 459 rc = tee_shm_pool_mgr_alloc_res_mem(vaddr, paddr, sz, 460 3 /* 8 bytes aligned */); 461 if (IS_ERR(rc)) 462 goto err_memunmap; 463 priv_mgr = rc; 464 465 vaddr += sz; 466 paddr += sz; 467 size -= sz; 468 } 469 470 rc = tee_shm_pool_mgr_alloc_res_mem(vaddr, paddr, size, PAGE_SHIFT); 471 if (IS_ERR(rc)) 472 goto err_free_priv_mgr; 473 dmabuf_mgr = rc; 474 475 rc = tee_shm_pool_alloc(priv_mgr, dmabuf_mgr); 476 if (IS_ERR(rc)) 477 goto err_free_dmabuf_mgr; 478 479 *memremaped_shm = va; 480 481 return rc; 482 483 err_free_dmabuf_mgr: 484 tee_shm_pool_mgr_destroy(dmabuf_mgr); 485 err_free_priv_mgr: 486 tee_shm_pool_mgr_destroy(priv_mgr); 487 err_memunmap: 488 memunmap(va); 489 return rc; 490 } 491 492 /* Simple wrapper functions to be able to use a function pointer */ 493 static void optee_smccc_smc(unsigned long a0, unsigned long a1, 494 unsigned long a2, unsigned long a3, 495 unsigned long a4, unsigned long a5, 496 unsigned long a6, unsigned long a7, 497 struct arm_smccc_res *res) 498 { 499 arm_smccc_smc(a0, a1, a2, a3, a4, a5, a6, a7, res); 500 } 501 502 static void optee_smccc_hvc(unsigned long a0, unsigned long a1, 503 unsigned long a2, unsigned long a3, 504 unsigned long a4, unsigned long a5, 505 unsigned long a6, unsigned long a7, 506 struct arm_smccc_res *res) 507 { 508 arm_smccc_hvc(a0, a1, a2, a3, a4, a5, a6, a7, res); 509 } 510 511 static optee_invoke_fn *get_invoke_func(struct device_node *np) 512 { 513 const char *method; 514 515 pr_info("probing for conduit method from DT.\n"); 516 517 if (of_property_read_string(np, "method", &method)) { 518 pr_warn("missing \"method\" property\n"); 519 return ERR_PTR(-ENXIO); 520 } 521 522 if (!strcmp("hvc", method)) 523 return optee_smccc_hvc; 524 else if (!strcmp("smc", method)) 525 return optee_smccc_smc; 526 527 pr_warn("invalid \"method\" property: %s\n", method); 528 return ERR_PTR(-EINVAL); 529 } 530 531 static struct optee *optee_probe(struct device_node *np) 532 { 533 optee_invoke_fn *invoke_fn; 534 struct tee_shm_pool *pool; 535 struct optee *optee = NULL; 536 void *memremaped_shm = NULL; 537 struct tee_device *teedev; 538 u32 sec_caps; 539 int rc; 540 541 invoke_fn = get_invoke_func(np); 542 if (IS_ERR(invoke_fn)) 543 return (void *)invoke_fn; 544 545 if (!optee_msg_api_uid_is_optee_api(invoke_fn)) { 546 pr_warn("api uid mismatch\n"); 547 return ERR_PTR(-EINVAL); 548 } 549 550 if (!optee_msg_api_revision_is_compatible(invoke_fn)) { 551 pr_warn("api revision mismatch\n"); 552 return ERR_PTR(-EINVAL); 553 } 554 555 if (!optee_msg_exchange_capabilities(invoke_fn, &sec_caps)) { 556 pr_warn("capabilities mismatch\n"); 557 return ERR_PTR(-EINVAL); 558 } 559 560 /* 561 * We have no other option for shared memory, if secure world 562 * doesn't have any reserved memory we can use we can't continue. 563 */ 564 if (!(sec_caps & OPTEE_SMC_SEC_CAP_HAVE_RESERVED_SHM)) 565 return ERR_PTR(-EINVAL); 566 567 pool = optee_config_shm_memremap(invoke_fn, &memremaped_shm, sec_caps); 568 if (IS_ERR(pool)) 569 return (void *)pool; 570 571 optee = kzalloc(sizeof(*optee), GFP_KERNEL); 572 if (!optee) { 573 rc = -ENOMEM; 574 goto err; 575 } 576 577 optee->invoke_fn = invoke_fn; 578 optee->sec_caps = sec_caps; 579 580 teedev = tee_device_alloc(&optee_desc, NULL, pool, optee); 581 if (IS_ERR(teedev)) { 582 rc = PTR_ERR(teedev); 583 goto err; 584 } 585 optee->teedev = teedev; 586 587 teedev = tee_device_alloc(&optee_supp_desc, NULL, pool, optee); 588 if (IS_ERR(teedev)) { 589 rc = PTR_ERR(teedev); 590 goto err; 591 } 592 optee->supp_teedev = teedev; 593 594 rc = tee_device_register(optee->teedev); 595 if (rc) 596 goto err; 597 598 rc = tee_device_register(optee->supp_teedev); 599 if (rc) 600 goto err; 601 602 mutex_init(&optee->call_queue.mutex); 603 INIT_LIST_HEAD(&optee->call_queue.waiters); 604 optee_wait_queue_init(&optee->wait_queue); 605 optee_supp_init(&optee->supp); 606 optee->memremaped_shm = memremaped_shm; 607 optee->pool = pool; 608 609 optee_enable_shm_cache(optee); 610 611 pr_info("initialized driver\n"); 612 return optee; 613 err: 614 if (optee) { 615 /* 616 * tee_device_unregister() is safe to call even if the 617 * devices hasn't been registered with 618 * tee_device_register() yet. 619 */ 620 tee_device_unregister(optee->supp_teedev); 621 tee_device_unregister(optee->teedev); 622 kfree(optee); 623 } 624 if (pool) 625 tee_shm_pool_free(pool); 626 if (memremaped_shm) 627 memunmap(memremaped_shm); 628 return ERR_PTR(rc); 629 } 630 631 static void optee_remove(struct optee *optee) 632 { 633 /* 634 * Ask OP-TEE to free all cached shared memory objects to decrease 635 * reference counters and also avoid wild pointers in secure world 636 * into the old shared memory range. 637 */ 638 optee_disable_shm_cache(optee); 639 640 /* 641 * The two devices has to be unregistered before we can free the 642 * other resources. 643 */ 644 tee_device_unregister(optee->supp_teedev); 645 tee_device_unregister(optee->teedev); 646 647 tee_shm_pool_free(optee->pool); 648 if (optee->memremaped_shm) 649 memunmap(optee->memremaped_shm); 650 optee_wait_queue_exit(&optee->wait_queue); 651 optee_supp_uninit(&optee->supp); 652 mutex_destroy(&optee->call_queue.mutex); 653 654 kfree(optee); 655 } 656 657 static const struct of_device_id optee_match[] = { 658 { .compatible = "linaro,optee-tz" }, 659 {}, 660 }; 661 662 static struct optee *optee_svc; 663 664 static int __init optee_driver_init(void) 665 { 666 struct device_node *fw_np; 667 struct device_node *np; 668 struct optee *optee; 669 670 /* Node is supposed to be below /firmware */ 671 fw_np = of_find_node_by_name(NULL, "firmware"); 672 if (!fw_np) 673 return -ENODEV; 674 675 np = of_find_matching_node(fw_np, optee_match); 676 if (!np) 677 return -ENODEV; 678 679 optee = optee_probe(np); 680 of_node_put(np); 681 682 if (IS_ERR(optee)) 683 return PTR_ERR(optee); 684 685 optee_svc = optee; 686 687 return 0; 688 } 689 module_init(optee_driver_init); 690 691 static void __exit optee_driver_exit(void) 692 { 693 struct optee *optee = optee_svc; 694 695 optee_svc = NULL; 696 if (optee) 697 optee_remove(optee); 698 } 699 module_exit(optee_driver_exit); 700 701 MODULE_AUTHOR("Linaro"); 702 MODULE_DESCRIPTION("OP-TEE driver"); 703 MODULE_SUPPORTED_DEVICE(""); 704 MODULE_VERSION("1.0"); 705 MODULE_LICENSE("GPL v2"); 706