@@ -445,6 +445,148 @@ static void __nvmem_device_put(struct nvmem_device *nvmem)
445
445
mutex_unlock (& nvmem_mutex );
446
446
}
447
447
448
+ static int nvmem_match (struct device * dev , void * data )
449
+ {
450
+ return !strcmp (dev_name (dev ), data );
451
+ }
452
+
453
+ static struct nvmem_device * nvmem_find (const char * name )
454
+ {
455
+ struct device * d ;
456
+
457
+ d = bus_find_device (& nvmem_bus_type , NULL , (void * )name , nvmem_match );
458
+
459
+ if (!d )
460
+ return NULL ;
461
+
462
+ return to_nvmem_device (d );
463
+ }
464
+
465
+ #if IS_ENABLED (CONFIG_NVMEM ) && IS_ENABLED (CONFIG_OF )
466
+ /**
467
+ * of_nvmem_device_get() - Get nvmem device from a given id
468
+ *
469
+ * @dev node: Device tree node that uses the nvmem device
470
+ * @id: nvmem name from nvmem-names property.
471
+ *
472
+ * Return: ERR_PTR() on error or a valid pointer to a struct nvmem_device
473
+ * on success.
474
+ */
475
+ struct nvmem_device * of_nvmem_device_get (struct device_node * np , const char * id )
476
+ {
477
+
478
+ struct device_node * nvmem_np ;
479
+ int index ;
480
+
481
+ index = of_property_match_string (np , "nvmem-names" , id );
482
+
483
+ nvmem_np = of_parse_phandle (np , "nvmem" , index );
484
+ if (!nvmem_np )
485
+ return ERR_PTR (- EINVAL );
486
+
487
+ return __nvmem_device_get (nvmem_np , NULL , NULL );
488
+ }
489
+ EXPORT_SYMBOL_GPL (of_nvmem_device_get );
490
+ #endif
491
+
492
+ /**
493
+ * nvmem_device_get() - Get nvmem device from a given id
494
+ *
495
+ * @dev : Device that uses the nvmem device
496
+ * @id: nvmem name from nvmem-names property.
497
+ *
498
+ * Return: ERR_PTR() on error or a valid pointer to a struct nvmem_device
499
+ * on success.
500
+ */
501
+ struct nvmem_device * nvmem_device_get (struct device * dev , const char * dev_name )
502
+ {
503
+ if (dev -> of_node ) { /* try dt first */
504
+ struct nvmem_device * nvmem ;
505
+
506
+ nvmem = of_nvmem_device_get (dev -> of_node , dev_name );
507
+
508
+ if (!IS_ERR (nvmem ) || PTR_ERR (nvmem ) == - EPROBE_DEFER )
509
+ return nvmem ;
510
+
511
+ }
512
+
513
+ return nvmem_find (dev_name );
514
+ }
515
+ EXPORT_SYMBOL_GPL (nvmem_device_get );
516
+
517
+ static int devm_nvmem_device_match (struct device * dev , void * res , void * data )
518
+ {
519
+ struct nvmem_device * * nvmem = res ;
520
+
521
+ if (WARN_ON (!nvmem || !* nvmem ))
522
+ return 0 ;
523
+
524
+ return * nvmem == data ;
525
+ }
526
+
527
+ static void devm_nvmem_device_release (struct device * dev , void * res )
528
+ {
529
+ nvmem_device_put (* (struct nvmem_device * * )res );
530
+ }
531
+
532
+ /**
533
+ * devm_nvmem_device_put() - put alredy got nvmem device
534
+ *
535
+ * @nvmem: pointer to nvmem device allocated by devm_nvmem_cell_get(),
536
+ * that needs to be released.
537
+ */
538
+ void devm_nvmem_device_put (struct device * dev , struct nvmem_device * nvmem )
539
+ {
540
+ int ret ;
541
+
542
+ ret = devres_release (dev , devm_nvmem_device_release ,
543
+ devm_nvmem_device_match , nvmem );
544
+
545
+ WARN_ON (ret );
546
+ }
547
+ EXPORT_SYMBOL_GPL (devm_nvmem_device_put );
548
+
549
+ /**
550
+ * nvmem_device_put() - put alredy got nvmem device
551
+ *
552
+ * @nvmem: pointer to nvmem device that needs to be released.
553
+ */
554
+ void nvmem_device_put (struct nvmem_device * nvmem )
555
+ {
556
+ __nvmem_device_put (nvmem );
557
+ }
558
+ EXPORT_SYMBOL_GPL (nvmem_device_put );
559
+
560
+ /**
561
+ * devm_nvmem_device_get() - Get nvmem cell of device form a given id
562
+ *
563
+ * @dev node: Device tree node that uses the nvmem cell
564
+ * @id: nvmem name in nvmems property.
565
+ *
566
+ * Return: ERR_PTR() on error or a valid pointer to a struct nvmem_cell
567
+ * on success. The nvmem_cell will be freed by the automatically once the
568
+ * device is freed.
569
+ */
570
+ struct nvmem_device * devm_nvmem_device_get (struct device * dev , const char * id )
571
+ {
572
+ struct nvmem_device * * ptr , * nvmem ;
573
+
574
+ ptr = devres_alloc (devm_nvmem_device_release , sizeof (* ptr ), GFP_KERNEL );
575
+ if (!ptr )
576
+ return ERR_PTR (- ENOMEM );
577
+
578
+ nvmem = nvmem_device_get (dev , id );
579
+ if (!IS_ERR (nvmem )) {
580
+ * ptr = nvmem ;
581
+ devres_add (dev , ptr );
582
+ } else {
583
+ devres_free (ptr );
584
+ }
585
+
586
+ return nvmem ;
587
+ }
588
+ EXPORT_SYMBOL_GPL (devm_nvmem_device_get );
589
+
448
590
static struct nvmem_cell * nvmem_cell_get_from_list (const char * cell_id )
449
591
{
450
592
struct nvmem_cell * cell = NULL ;
@@ -806,6 +948,122 @@ int nvmem_cell_write(struct nvmem_cell *cell, void *buf, size_t len)
806
948
}
807
949
EXPORT_SYMBOL_GPL (nvmem_cell_write );
808
950
951
+ /**
952
+ * nvmem_device_cell_read() - Read a given nvmem device and cell
953
+ *
954
+ * @nvmem: nvmem device to read from.
955
+ * @info: nvmem cell info to be read.
956
+ * @buf: buffer pointer which will be populated on successful read.
957
+ *
958
+ * Return: length of successful bytes read on success and negative
959
+ * error code on error.
960
+ */
961
+ ssize_t nvmem_device_cell_read (struct nvmem_device * nvmem ,
962
+ struct nvmem_cell_info * info , void * buf )
963
+ {
964
+ struct nvmem_cell cell ;
965
+ int rc ;
966
+ ssize_t len ;
967
+
968
+ if (!nvmem || !nvmem -> regmap )
969
+ return - EINVAL ;
970
+
971
+ rc = nvmem_cell_info_to_nvmem_cell (nvmem , info , & cell );
972
+ if (IS_ERR_VALUE (rc ))
973
+ return rc ;
974
+
975
+ rc = __nvmem_cell_read (nvmem , & cell , buf , & len );
976
+ if (IS_ERR_VALUE (rc ))
977
+ return rc ;
978
+
979
+ return len ;
980
+ }
981
+ EXPORT_SYMBOL_GPL (nvmem_device_cell_read );
982
+
983
+ /**
984
+ * nvmem_device_cell_write() - Write cell to a given nvmem device
985
+ *
986
+ * @nvmem: nvmem device to be written to.
987
+ * @info: nvmem cell info to be written
988
+ * @buf: buffer to be written to cell.
989
+ *
990
+ * Return: length of bytes written or negative error code on failure.
991
+ * */
992
+ int nvmem_device_cell_write (struct nvmem_device * nvmem ,
993
+ struct nvmem_cell_info * info , void * buf )
994
+ {
995
+ struct nvmem_cell cell ;
996
+ int rc ;
997
+
998
+ if (!nvmem || !nvmem -> regmap )
999
+ return - EINVAL ;
1000
+
1001
+ rc = nvmem_cell_info_to_nvmem_cell (nvmem , info , & cell );
1002
+ if (IS_ERR_VALUE (rc ))
1003
+ return rc ;
1004
+
1005
+ return nvmem_cell_write (& cell , buf , cell .bytes );
1006
+ }
1007
+ EXPORT_SYMBOL_GPL (nvmem_device_cell_write );
1008
+
1009
+ /**
1010
+ * nvmem_device_read() - Read from a given nvmem device
1011
+ *
1012
+ * @nvmem: nvmem device to read from.
1013
+ * @offset: offset in nvmem device.
1014
+ * @bytes: number of bytes to read.
1015
+ * @buf: buffer pointer which will be populated on successful read.
1016
+ *
1017
+ * Return: length of successful bytes read on success and negative
1018
+ * error code on error.
1019
+ */
1020
+ int nvmem_device_read (struct nvmem_device * nvmem ,
1021
+ unsigned int offset ,
1022
+ size_t bytes , void * buf )
1023
+ {
1024
+ int rc ;
1025
+
1026
+ if (!nvmem || !nvmem -> regmap )
1027
+ return - EINVAL ;
1028
+
1029
+ rc = regmap_raw_read (nvmem -> regmap , offset , buf , bytes );
1030
+
1031
+ if (IS_ERR_VALUE (rc ))
1032
+ return rc ;
1033
+
1034
+ return bytes ;
1035
+ }
1036
+ EXPORT_SYMBOL_GPL (nvmem_device_read );
1037
+
1038
+ /**
1039
+ * nvmem_device_write() - Write cell to a given nvmem device
1040
+ *
1041
+ * @nvmem: nvmem device to be written to.
1042
+ * @offset: offset in nvmem device.
1043
+ * @bytes: number of bytes to write.
1044
+ * @buf: buffer to be written.
1045
+ *
1046
+ * Return: length of bytes written or negative error code on failure.
1047
+ * */
1048
+ int nvmem_device_write (struct nvmem_device * nvmem ,
1049
+ unsigned int offset ,
1050
+ size_t bytes , void * buf )
1051
+ {
1052
+ int rc ;
1053
+
1054
+ if (!nvmem || !nvmem -> regmap )
1055
+ return - EINVAL ;
1056
+
1057
+ rc = regmap_raw_write (nvmem -> regmap , offset , buf , bytes );
1058
+
1059
+ if (IS_ERR_VALUE (rc ))
1060
+ return rc ;
1061
+
1062
+
1063
+ return bytes ;
1064
+ }
1065
+ EXPORT_SYMBOL_GPL (nvmem_device_write );
1066
+
809
1067
static int __init nvmem_init (void )
810
1068
{
811
1069
return bus_register (& nvmem_bus_type );
0 commit comments