~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

TOMOYO Linux Cross Reference
Linux/Documentation/driver-api/nvmem.rst

Version: ~ [ linux-6.11.5 ] ~ [ linux-6.10.14 ] ~ [ linux-6.9.12 ] ~ [ linux-6.8.12 ] ~ [ linux-6.7.12 ] ~ [ linux-6.6.58 ] ~ [ linux-6.5.13 ] ~ [ linux-6.4.16 ] ~ [ linux-6.3.13 ] ~ [ linux-6.2.16 ] ~ [ linux-6.1.114 ] ~ [ linux-6.0.19 ] ~ [ linux-5.19.17 ] ~ [ linux-5.18.19 ] ~ [ linux-5.17.15 ] ~ [ linux-5.16.20 ] ~ [ linux-5.15.169 ] ~ [ linux-5.14.21 ] ~ [ linux-5.13.19 ] ~ [ linux-5.12.19 ] ~ [ linux-5.11.22 ] ~ [ linux-5.10.228 ] ~ [ linux-5.9.16 ] ~ [ linux-5.8.18 ] ~ [ linux-5.7.19 ] ~ [ linux-5.6.19 ] ~ [ linux-5.5.19 ] ~ [ linux-5.4.284 ] ~ [ linux-5.3.18 ] ~ [ linux-5.2.21 ] ~ [ linux-5.1.21 ] ~ [ linux-5.0.21 ] ~ [ linux-4.20.17 ] ~ [ linux-4.19.322 ] ~ [ linux-4.18.20 ] ~ [ linux-4.17.19 ] ~ [ linux-4.16.18 ] ~ [ linux-4.15.18 ] ~ [ linux-4.14.336 ] ~ [ linux-4.13.16 ] ~ [ linux-4.12.14 ] ~ [ linux-4.11.12 ] ~ [ linux-4.10.17 ] ~ [ linux-4.9.337 ] ~ [ linux-4.4.302 ] ~ [ linux-3.10.108 ] ~ [ linux-2.6.32.71 ] ~ [ linux-2.6.0 ] ~ [ linux-2.4.37.11 ] ~ [ unix-v6-master ] ~ [ ccs-tools-1.8.9 ] ~ [ policy-sample ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

  1 .. SPDX-License-Identifier: GPL-2.0
  2 
  3 ===============
  4 NVMEM Subsystem
  5 ===============
  6 
  7  Srinivas Kandagatla <srinivas.kandagatla@linaro.org>
  8 
  9 This document explains the NVMEM Framework along with the APIs provided,
 10 and how to use it.
 11 
 12 1. Introduction
 13 ===============
 14 *NVMEM* is the abbreviation for Non Volatile Memory layer. It is used to
 15 retrieve configuration of SOC or Device specific data from non volatile
 16 memories like eeprom, efuses and so on.
 17 
 18 Before this framework existed, NVMEM drivers like eeprom were stored in
 19 drivers/misc, where they all had to duplicate pretty much the same code to
 20 register a sysfs file, allow in-kernel users to access the content of the
 21 devices they were driving, etc.
 22 
 23 This was also a problem as far as other in-kernel users were involved, since
 24 the solutions used were pretty much different from one driver to another, there
 25 was a rather big abstraction leak.
 26 
 27 This framework aims at solve these problems. It also introduces DT
 28 representation for consumer devices to go get the data they require (MAC
 29 Addresses, SoC/Revision ID, part numbers, and so on) from the NVMEMs.
 30 
 31 NVMEM Providers
 32 +++++++++++++++
 33 
 34 NVMEM provider refers to an entity that implements methods to initialize, read
 35 and write the non-volatile memory.
 36 
 37 2. Registering/Unregistering the NVMEM provider
 38 ===============================================
 39 
 40 A NVMEM provider can register with NVMEM core by supplying relevant
 41 nvmem configuration to nvmem_register(), on success core would return a valid
 42 nvmem_device pointer.
 43 
 44 nvmem_unregister() is used to unregister a previously registered provider.
 45 
 46 For example, a simple nvram case::
 47 
 48   static int brcm_nvram_probe(struct platform_device *pdev)
 49   {
 50         struct nvmem_config config = {
 51                 .name = "brcm-nvram",
 52                 .reg_read = brcm_nvram_read,
 53         };
 54         ...
 55         config.dev = &pdev->dev;
 56         config.priv = priv;
 57         config.size = resource_size(res);
 58 
 59         devm_nvmem_register(&config);
 60   }
 61 
 62 Users of board files can define and register nvmem cells using the
 63 nvmem_cell_table struct::
 64 
 65   static struct nvmem_cell_info foo_nvmem_cells[] = {
 66         {
 67                 .name           = "macaddr",
 68                 .offset         = 0x7f00,
 69                 .bytes          = ETH_ALEN,
 70         }
 71   };
 72 
 73   static struct nvmem_cell_table foo_nvmem_cell_table = {
 74         .nvmem_name             = "i2c-eeprom",
 75         .cells                  = foo_nvmem_cells,
 76         .ncells                 = ARRAY_SIZE(foo_nvmem_cells),
 77   };
 78 
 79   nvmem_add_cell_table(&foo_nvmem_cell_table);
 80 
 81 Additionally it is possible to create nvmem cell lookup entries and register
 82 them with the nvmem framework from machine code as shown in the example below::
 83 
 84   static struct nvmem_cell_lookup foo_nvmem_lookup = {
 85         .nvmem_name             = "i2c-eeprom",
 86         .cell_name              = "macaddr",
 87         .dev_id                 = "foo_mac.0",
 88         .con_id                 = "mac-address",
 89   };
 90 
 91   nvmem_add_cell_lookups(&foo_nvmem_lookup, 1);
 92 
 93 NVMEM Consumers
 94 +++++++++++++++
 95 
 96 NVMEM consumers are the entities which make use of the NVMEM provider to
 97 read from and to NVMEM.
 98 
 99 3. NVMEM cell based consumer APIs
100 =================================
101 
102 NVMEM cells are the data entries/fields in the NVMEM.
103 The NVMEM framework provides 3 APIs to read/write NVMEM cells::
104 
105   struct nvmem_cell *nvmem_cell_get(struct device *dev, const char *name);
106   struct nvmem_cell *devm_nvmem_cell_get(struct device *dev, const char *name);
107 
108   void nvmem_cell_put(struct nvmem_cell *cell);
109   void devm_nvmem_cell_put(struct device *dev, struct nvmem_cell *cell);
110 
111   void *nvmem_cell_read(struct nvmem_cell *cell, ssize_t *len);
112   int nvmem_cell_write(struct nvmem_cell *cell, void *buf, ssize_t len);
113 
114 `*nvmem_cell_get()` apis will get a reference to nvmem cell for a given id,
115 and nvmem_cell_read/write() can then read or write to the cell.
116 Once the usage of the cell is finished the consumer should call
117 `*nvmem_cell_put()` to free all the allocation memory for the cell.
118 
119 4. Direct NVMEM device based consumer APIs
120 ==========================================
121 
122 In some instances it is necessary to directly read/write the NVMEM.
123 To facilitate such consumers NVMEM framework provides below apis::
124 
125   struct nvmem_device *nvmem_device_get(struct device *dev, const char *name);
126   struct nvmem_device *devm_nvmem_device_get(struct device *dev,
127                                            const char *name);
128   struct nvmem_device *nvmem_device_find(void *data,
129                         int (*match)(struct device *dev, const void *data));
130   void nvmem_device_put(struct nvmem_device *nvmem);
131   int nvmem_device_read(struct nvmem_device *nvmem, unsigned int offset,
132                       size_t bytes, void *buf);
133   int nvmem_device_write(struct nvmem_device *nvmem, unsigned int offset,
134                        size_t bytes, void *buf);
135   int nvmem_device_cell_read(struct nvmem_device *nvmem,
136                            struct nvmem_cell_info *info, void *buf);
137   int nvmem_device_cell_write(struct nvmem_device *nvmem,
138                             struct nvmem_cell_info *info, void *buf);
139 
140 Before the consumers can read/write NVMEM directly, it should get hold
141 of nvmem_controller from one of the `*nvmem_device_get()` api.
142 
143 The difference between these apis and cell based apis is that these apis always
144 take nvmem_device as parameter.
145 
146 5. Releasing a reference to the NVMEM
147 =====================================
148 
149 When a consumer no longer needs the NVMEM, it has to release the reference
150 to the NVMEM it has obtained using the APIs mentioned in the above section.
151 The NVMEM framework provides 2 APIs to release a reference to the NVMEM::
152 
153   void nvmem_cell_put(struct nvmem_cell *cell);
154   void devm_nvmem_cell_put(struct device *dev, struct nvmem_cell *cell);
155   void nvmem_device_put(struct nvmem_device *nvmem);
156   void devm_nvmem_device_put(struct device *dev, struct nvmem_device *nvmem);
157 
158 Both these APIs are used to release a reference to the NVMEM and
159 devm_nvmem_cell_put and devm_nvmem_device_put destroys the devres associated
160 with this NVMEM.
161 
162 Userspace
163 +++++++++
164 
165 6. Userspace binary interface
166 ==============================
167 
168 Userspace can read/write the raw NVMEM file located at::
169 
170         /sys/bus/nvmem/devices/*/nvmem
171 
172 ex::
173 
174   hexdump /sys/bus/nvmem/devices/qfprom0/nvmem
175 
176   0000000 0000 0000 0000 0000 0000 0000 0000 0000
177   *
178   00000a0 db10 2240 0000 e000 0c00 0c00 0000 0c00
179   0000000 0000 0000 0000 0000 0000 0000 0000 0000
180   ...
181   *
182   0001000
183 
184 7. DeviceTree Binding
185 =====================
186 
187 See Documentation/devicetree/bindings/nvmem/nvmem.txt
188 
189 8. NVMEM layouts
190 ================
191 
192 NVMEM layouts are yet another mechanism to create cells. With the device
193 tree binding it is possible to specify simple cells by using an offset
194 and a length. Sometimes, the cells doesn't have a static offset, but
195 the content is still well defined, e.g. tag-length-values. In this case,
196 the NVMEM device content has to be first parsed and the cells need to
197 be added accordingly. Layouts let you read the content of the NVMEM device
198 and let you add cells dynamically.
199 
200 Another use case for layouts is the post processing of cells. With layouts,
201 it is possible to associate a custom post processing hook to a cell. It
202 even possible to add this hook to cells not created by the layout itself.
203 
204 9. Internal kernel API
205 ======================
206 
207 .. kernel-doc:: drivers/nvmem/core.c
208    :export:

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

kernel.org | git.kernel.org | LWN.net | Project Home | SVN repository | Mail admin

Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.

sflogo.php