1 // SPDX-License-Identifier: GPL-2.0
3 #include <linux/blkdev.h>
4 #include <linux/major.h>
6 #include <linux/string.h>
9 static int validate_of_partition(struct device_node
*np
, int slot
)
14 const __be32
*reg
= of_get_property(np
, "reg", &len
);
15 int a_cells
= of_n_addr_cells(np
);
16 int s_cells
= of_n_size_cells(np
);
18 /* Make sure reg len match the expected addr and size cells */
19 if (len
/ sizeof(*reg
) != a_cells
+ s_cells
)
22 /* Validate offset conversion from bytes to sectors */
23 offset
= of_read_number(reg
, a_cells
);
24 if (offset
% SECTOR_SIZE
)
27 /* Validate size conversion from bytes to sectors */
28 size
= of_read_number(reg
+ a_cells
, s_cells
);
29 if (!size
|| size
% SECTOR_SIZE
)
35 static void add_of_partition(struct parsed_partitions
*state
, int slot
,
36 struct device_node
*np
)
38 struct partition_meta_info
*info
;
39 char tmp
[sizeof(info
->volname
) + 4];
43 const __be32
*reg
= of_get_property(np
, "reg", &len
);
44 int a_cells
= of_n_addr_cells(np
);
45 int s_cells
= of_n_size_cells(np
);
47 /* Convert bytes to sector size */
48 u64 offset
= of_read_number(reg
, a_cells
) / SECTOR_SIZE
;
49 u64 size
= of_read_number(reg
+ a_cells
, s_cells
) / SECTOR_SIZE
;
51 put_partition(state
, slot
, offset
, size
);
53 if (of_property_read_bool(np
, "read-only"))
54 state
->parts
[slot
].flags
|= ADDPART_FLAG_READONLY
;
57 * Follow MTD label logic, search for label property,
58 * fallback to node name if not found.
60 info
= &state
->parts
[slot
].info
;
61 partname
= of_get_property(np
, "label", &len
);
63 partname
= of_get_property(np
, "name", &len
);
64 strscpy(info
->volname
, partname
, sizeof(info
->volname
));
66 snprintf(tmp
, sizeof(tmp
), "(%s)", info
->volname
);
67 strlcat(state
->pp_buf
, tmp
, PAGE_SIZE
);
70 int of_partition(struct parsed_partitions
*state
)
72 struct device
*ddev
= disk_to_dev(state
->disk
);
73 struct device_node
*np
;
76 struct device_node
*partitions_np
= of_node_get(ddev
->of_node
);
79 !of_device_is_compatible(partitions_np
, "fixed-partitions"))
83 /* Validate parition offset and size */
84 for_each_child_of_node(partitions_np
, np
) {
85 if (validate_of_partition(np
, slot
)) {
87 of_node_put(partitions_np
);
96 for_each_child_of_node(partitions_np
, np
) {
97 if (slot
>= state
->limit
) {
102 add_of_partition(state
, slot
, np
);
107 strlcat(state
->pp_buf
, "\n", PAGE_SIZE
);