@@ -354,15 +354,64 @@ tee_ioctl_shm_register(struct tee_context *ctx,
354354 return ret ;
355355}
356356
357+ static int param_from_user_memref (struct tee_context * ctx ,
358+ struct tee_param_memref * memref ,
359+ struct tee_ioctl_param * ip )
360+ {
361+ struct tee_shm * shm ;
362+
363+ /*
364+ * If a NULL pointer is passed to a TA in the TEE,
365+ * the ip.c IOCTL parameters is set to TEE_MEMREF_NULL
366+ * indicating a NULL memory reference.
367+ */
368+ if (ip -> c != TEE_MEMREF_NULL ) {
369+ /*
370+ * If we fail to get a pointer to a shared
371+ * memory object (and increase the ref count)
372+ * from an identifier we return an error. All
373+ * pointers that has been added in params have
374+ * an increased ref count. It's the callers
375+ * responibility to do tee_shm_put() on all
376+ * resolved pointers.
377+ */
378+ shm = tee_shm_get_from_id (ctx , ip -> c );
379+ if (IS_ERR (shm ))
380+ return PTR_ERR (shm );
381+
382+ /*
383+ * Ensure offset + size does not overflow
384+ * offset and does not overflow the size of
385+ * the referred shared memory object.
386+ */
387+ if ((ip -> a + ip -> b ) < ip -> a ||
388+ (ip -> a + ip -> b ) > shm -> size ) {
389+ tee_shm_put (shm );
390+ return - EINVAL ;
391+ }
392+ } else if (ctx -> cap_memref_null ) {
393+ /* Pass NULL pointer to OP-TEE */
394+ shm = NULL ;
395+ } else {
396+ return - EINVAL ;
397+ }
398+
399+ memref -> shm_offs = ip -> a ;
400+ memref -> size = ip -> b ;
401+ memref -> shm = shm ;
402+
403+ return 0 ;
404+ }
405+
357406static int params_from_user (struct tee_context * ctx , struct tee_param * params ,
358407 size_t num_params ,
359408 struct tee_ioctl_param __user * uparams )
360409{
361410 size_t n ;
362411
363412 for (n = 0 ; n < num_params ; n ++ ) {
364- struct tee_shm * shm ;
365413 struct tee_ioctl_param ip ;
414+ int rc ;
366415
367416 if (copy_from_user (& ip , uparams + n , sizeof (ip )))
368417 return - EFAULT ;
@@ -385,45 +434,10 @@ static int params_from_user(struct tee_context *ctx, struct tee_param *params,
385434 case TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_INPUT :
386435 case TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_OUTPUT :
387436 case TEE_IOCTL_PARAM_ATTR_TYPE_MEMREF_INOUT :
388- /*
389- * If a NULL pointer is passed to a TA in the TEE,
390- * the ip.c IOCTL parameters is set to TEE_MEMREF_NULL
391- * indicating a NULL memory reference.
392- */
393- if (ip .c != TEE_MEMREF_NULL ) {
394- /*
395- * If we fail to get a pointer to a shared
396- * memory object (and increase the ref count)
397- * from an identifier we return an error. All
398- * pointers that has been added in params have
399- * an increased ref count. It's the callers
400- * responibility to do tee_shm_put() on all
401- * resolved pointers.
402- */
403- shm = tee_shm_get_from_id (ctx , ip .c );
404- if (IS_ERR (shm ))
405- return PTR_ERR (shm );
406-
407- /*
408- * Ensure offset + size does not overflow
409- * offset and does not overflow the size of
410- * the referred shared memory object.
411- */
412- if ((ip .a + ip .b ) < ip .a ||
413- (ip .a + ip .b ) > shm -> size ) {
414- tee_shm_put (shm );
415- return - EINVAL ;
416- }
417- } else if (ctx -> cap_memref_null ) {
418- /* Pass NULL pointer to OP-TEE */
419- shm = NULL ;
420- } else {
421- return - EINVAL ;
422- }
423-
424- params [n ].u .memref .shm_offs = ip .a ;
425- params [n ].u .memref .size = ip .b ;
426- params [n ].u .memref .shm = shm ;
437+ rc = param_from_user_memref (ctx , & params [n ].u .memref ,
438+ & ip );
439+ if (rc )
440+ return rc ;
427441 break ;
428442 default :
429443 /* Unknown attribute */
0 commit comments