]>
Commit | Line | Data |
---|---|---|
31f18b77 FG |
1 | # List of valid osd flags |
2 | OSD_FLAGS = [ | |
3 | 'pause', 'noup', 'nodown', 'noout', 'noin', 'nobackfill', | |
4 | 'norecover', 'noscrub', 'nodeep-scrub', | |
5 | ] | |
6 | ||
7 | # Implemented osd commands | |
8 | OSD_IMPLEMENTED_COMMANDS = [ | |
f64942e4 | 9 | 'scrub', 'deep-scrub', 'repair' |
31f18b77 FG |
10 | ] |
11 | ||
12 | # Valid values for the 'var' argument to 'ceph osd pool set' | |
13 | POOL_PROPERTIES_1 = [ | |
11fdf7f2 TL |
14 | 'size', 'min_size', 'pg_num', |
15 | 'crush_rule', 'hashpspool', | |
31f18b77 FG |
16 | ] |
17 | ||
18 | POOL_PROPERTIES_2 = [ | |
19 | 'pgp_num' | |
20 | ] | |
21 | ||
22 | POOL_PROPERTIES = POOL_PROPERTIES_1 + POOL_PROPERTIES_2 | |
23 | ||
24 | # Valid values for the 'ceph osd pool set-quota' command | |
25 | POOL_QUOTA_PROPERTIES = [ | |
26 | ('quota_max_bytes', 'max_bytes'), | |
27 | ('quota_max_objects', 'max_objects'), | |
28 | ] | |
29 | ||
1adf2230 | 30 | POOL_ARGS = POOL_PROPERTIES + [x for x,_ in POOL_QUOTA_PROPERTIES] |
31f18b77 FG |
31 | |
32 | ||
33 | # Transform command to a human readable form | |
34 | def humanify_command(command): | |
35 | out = [command['prefix']] | |
36 | ||
9f95a23c | 37 | for arg, val in command.items(): |
31f18b77 FG |
38 | if arg != 'prefix': |
39 | out.append("%s=%s" % (str(arg), str(val))) | |
40 | ||
41 | return " ".join(out) | |
42 | ||
43 | ||
44 | def invalid_pool_args(args): | |
45 | invalid = [] | |
46 | for arg in args: | |
47 | if arg not in POOL_ARGS: | |
48 | invalid.append(arg) | |
49 | ||
50 | return invalid | |
51 | ||
52 | ||
53 | def pool_update_commands(pool_name, args): | |
54 | commands = [[], []] | |
55 | ||
56 | # We should increase pgp_num when we are re-setting pg_num | |
57 | if 'pg_num' in args and 'pgp_num' not in args: | |
58 | args['pgp_num'] = args['pg_num'] | |
59 | ||
60 | # Run the first pool set and quota properties in parallel | |
61 | for var in POOL_PROPERTIES_1: | |
62 | if var in args: | |
63 | commands[0].append({ | |
64 | 'prefix': 'osd pool set', | |
65 | 'pool': pool_name, | |
66 | 'var': var, | |
67 | 'val': args[var], | |
68 | }) | |
69 | ||
70 | for (var, field) in POOL_QUOTA_PROPERTIES: | |
71 | if var in args: | |
72 | commands[0].append({ | |
73 | 'prefix': 'osd pool set-quota', | |
74 | 'pool': pool_name, | |
75 | 'field': field, | |
76 | 'val': str(args[var]), | |
77 | }) | |
78 | ||
79 | # The second pool set properties need to be run after the first wave | |
80 | for var in POOL_PROPERTIES_2: | |
81 | if var in args: | |
82 | commands[1].append({ | |
83 | 'prefix': 'osd pool set', | |
84 | 'pool': pool_name, | |
85 | 'var': var, | |
28e407b8 | 86 | 'val': args[var], |
31f18b77 FG |
87 | }) |
88 | ||
89 | return commands | |
90 | ||
a8e16298 TL |
91 | def crush_rule_osds(node_buckets, rule): |
92 | nodes_by_id = dict((b['id'], b) for b in node_buckets) | |
31f18b77 | 93 | |
eafe8130 TL |
94 | def _gather_leaf_ids(node_id): |
95 | if node_id >= 0: | |
96 | return set([node_id]) | |
31f18b77 FG |
97 | |
98 | result = set() | |
eafe8130 TL |
99 | for item in nodes_by_id[node_id]['items']: |
100 | result |= _gather_leaf_ids(item['id']) | |
31f18b77 FG |
101 | |
102 | return result | |
103 | ||
104 | def _gather_descendent_ids(node, typ): | |
105 | result = set() | |
a8e16298 TL |
106 | for item in node['items']: |
107 | if item['id'] >= 0: | |
108 | if typ == "osd": | |
109 | result.add(item['id']) | |
110 | else: | |
111 | child_node = nodes_by_id[item['id']] | |
112 | if child_node['type_name'] == typ: | |
113 | result.add(child_node['id']) | |
114 | elif 'items' in child_node: | |
115 | result |= _gather_descendent_ids(child_node, typ) | |
31f18b77 FG |
116 | |
117 | return result | |
118 | ||
119 | def _gather_osds(root, steps): | |
120 | if root['id'] >= 0: | |
121 | return set([root['id']]) | |
122 | ||
123 | osds = set() | |
124 | step = steps[0] | |
125 | if step['op'] == 'choose_firstn': | |
126 | # Choose all descendents of the current node of type 'type' | |
a8e16298 TL |
127 | descendent_ids = _gather_descendent_ids(root, step['type']) |
128 | for node_id in descendent_ids: | |
129 | if node_id >= 0: | |
130 | osds.add(node_id) | |
131 | else: | |
132 | for desc_node in nodes_by_id[node_id]: | |
133 | osds |= _gather_osds(desc_node, steps[1:]) | |
31f18b77 FG |
134 | elif step['op'] == 'chooseleaf_firstn': |
135 | # Choose all descendents of the current node of type 'type', | |
136 | # and select all leaves beneath those | |
a8e16298 TL |
137 | descendent_ids = _gather_descendent_ids(root, step['type']) |
138 | for node_id in descendent_ids: | |
139 | if node_id >= 0: | |
140 | osds.add(node_id) | |
141 | else: | |
142 | for desc_node in nodes_by_id[node_id]['items']: | |
143 | # Short circuit another iteration to find the emit | |
144 | # and assume anything we've done a chooseleaf on | |
145 | # is going to be part of the selected set of osds | |
eafe8130 | 146 | osds |= _gather_leaf_ids(desc_node['id']) |
31f18b77 FG |
147 | elif step['op'] == 'emit': |
148 | if root['id'] >= 0: | |
149 | osds |= root['id'] | |
150 | ||
151 | return osds | |
152 | ||
153 | osds = set() | |
154 | for i, step in enumerate(rule['steps']): | |
155 | if step['op'] == 'take': | |
156 | osds |= _gather_osds(nodes_by_id[step['item']], rule['steps'][i + 1:]) | |
157 | return osds |