2 * This file is open source software, licensed to you under the terms
3 * of the Apache License, Version 2.0 (the "License"). See the NOTICE file
4 * distributed with this work for additional information regarding copyright
5 * ownership. You may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
9 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing,
12 * software distributed under the License is distributed on an
13 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14 * KIND, either express or implied. See the License for the
15 * specific language governing permissions and limitations
19 * Copyright (C) 2016 Scylla DB Ltd
24 #include <seastar/core/sstring.hh>
30 constexpr unsigned max_scheduling_groups() { return 16; }
32 template <typename... T>
37 class scheduling_group;
41 // Returns an index between 0 and max_scheduling_groups()
42 unsigned scheduling_group_index(scheduling_group sg);
43 scheduling_group scheduling_group_from_index(unsigned index);
48 /// Creates a scheduling group with a specified number of shares.
50 /// The operation is global and affects all shards. The returned scheduling
51 /// group can then be used in any shard.
53 /// \param name A name that identifiers the group; will be used as a label
54 /// in the group's metrics
55 /// \param shares number of shares of the CPU time allotted to the group;
56 /// Use numbers in the 1-1000 range (but can go above).
57 /// \return a scheduling group that can be used on any shard
58 future<scheduling_group> create_scheduling_group(sstring name, float shares);
60 /// Destroys a scheduling group.
62 /// Destroys a \ref scheduling_group previously created with create_scheduling_group().
63 /// The destroyed group must not be currently in use and must not be used later.
65 /// The operation is global and affects all shards.
67 /// \param sg The scheduling group to be destroyed
68 /// \return a future that is ready when the scheduling group has been torn down
69 future<> destroy_scheduling_group(scheduling_group sg);
71 /// \brief Identifies function calls that are accounted as a group
73 /// A `scheduling_group` is a tag that can be used to mark a function call.
74 /// Executions of such tagged calls are accounted as a group.
75 class scheduling_group {
78 explicit scheduling_group(unsigned id) : _id(id) {}
80 /// Creates a `scheduling_group` object denoting the default group
81 constexpr scheduling_group() noexcept : _id(0) {} // must be constexpr for current_scheduling_group_holder
83 const sstring& name() const;
84 bool operator==(scheduling_group x) const { return _id == x._id; }
85 bool operator!=(scheduling_group x) const { return _id != x._id; }
86 bool is_main() const { return _id == 0; }
87 /// Adjusts the number of shares allotted to the group.
89 /// Dynamically adjust the number of shares allotted to the group, increasing or
90 /// decreasing the amount of CPU bandwidth it gets. The adjustment is local to
93 /// This can be used to reduce a background job's interference with a foreground
94 /// load: the shares can be started at a low value, increased when the background
95 /// job's backlog increases, and reduced again when the backlog decreases.
97 /// \param shares number of shares allotted to the group. Use numbers
98 /// in the 1-1000 range.
99 void set_shares(float shares);
100 friend future<scheduling_group> create_scheduling_group(sstring name, float shares);
101 friend future<> destroy_scheduling_group(scheduling_group sg);
102 friend class reactor;
103 friend unsigned internal::scheduling_group_index(scheduling_group sg);
104 friend scheduling_group internal::scheduling_group_from_index(unsigned index);
112 scheduling_group_index(scheduling_group sg) {
118 scheduling_group_from_index(unsigned index) {
119 return scheduling_group(index);
124 current_scheduling_group_ptr() {
125 // Slow unless constructor is constexpr
126 static thread_local scheduling_group sg;
133 /// Returns the current scheduling group
136 current_scheduling_group() {
137 return *internal::current_scheduling_group_ptr();
142 default_scheduling_group() {
143 return scheduling_group();
148 scheduling_group::active() const {
149 return *this == current_scheduling_group();
157 struct hash<seastar::scheduling_group> {
158 size_t operator()(seastar::scheduling_group sg) const {
159 return seastar::internal::scheduling_group_index(sg);