MCPcopy Create free account
hub / github.com/XpuOS/xsched / LaunchHwCommand

Method LaunchHwCommand

preempt/src/xqueue/launch_worker.cpp:164–263  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

162}
163
164void LaunchWorker::LaunchHwCommand(std::shared_ptr<HwCommand> hw_cmd)
165{
166 XDEBG("launch hw_cmd (%p) idx " FMT_64D, hw_cmd.get(), hw_cmd->GetIdx());
167 // If a HwCommand is deactivated, all non-idempotent HwCommands launched after it should also
168 // be deactivated. Otherwise the XPU will become inconsist. So, if a HwCommand is not
169 // deactivatable, it should wait until all in-flight deactivatable HwCommands are completed.
170 // This is unnecessary under kPreemptLevelBlock.
171 bool wait_deactivatable = level_ >= kPreemptLevelDeactivate &&
172 (kCommandPropertyNone == hw_cmd->GetProps(
173 kCommandPropertyDeactivatable | kCommandPropertyIdempotent));
174
175 hw_cmd->BeforeLaunch();
176 std::unique_lock<MutexLock> lock(*mtx_);
177
178 // If the HwCommand is not deactivatable and non-idempoent,
179 // wait until all previous in-flight deactivatable HwCommand are completed.
180 if (wait_deactivatable) {
181 // Find the last synchronizable HwCommand after the last deactivatable HwCommand.
182 bool has_deactivatable = false;
183 std::shared_ptr<HwCommand> command_to_sync = nullptr;
184 for (auto it = cmd_log_.rbegin(); it != cmd_log_.rend(); ++it) {
185 if ((*it)->Synchronizable()) command_to_sync = *it;
186 if ((*it)->GetProps(kCommandPropertyDeactivatable)) {
187 has_deactivatable = true;
188 break;
189 }
190 }
191
192 if (has_deactivatable) {
193 // If there is a synchronizable HwCommand, sync it. Otherwise, sync the HwQueue.
194 lock = (command_to_sync == nullptr)
195 ? SyncAllWithLock(std::move(lock))
196 : SyncCmdWithLock(std::move(lock), command_to_sync);
197 }
198 }
199
200 if (cmd_log_.size() >= (size_t)threshold_) {
201 // The command log is full (in-flight HwCommand reaches threshold), wait for a empty slot.
202 std::shared_ptr<HwCommand> command_to_sync = nullptr;
203 int64_t front_command_idx = cmd_log_.front()->GetIdx();
204
205 for (auto cmd : sync_cmd_log_) {
206 // Make sure after syncing the HwCommand, there will be at least one empty slot.
207 if (cmd->GetIdx() >= front_command_idx) {
208 command_to_sync = cmd;
209 break;
210 }
211 }
212
213 // If there is a synchronizable HwCommand, sync it. Otherwise, sync the HwQueue.
214 lock = (command_to_sync == nullptr)
215 ? SyncAllWithLock(std::move(lock))
216 : SyncCmdWithLock(std::move(lock), command_to_sync);
217
218 } else {
219 // Wait if the worker is paused.
220 while (true) {
221 if (state_ == kWorkerStateRunning) {

Callers

nothing calls this directly

Calls 8

GetIdxMethod · 0.80
GetPropsMethod · 0.80
SetStateMethod · 0.80
BeforeLaunchMethod · 0.45
SynchronizableMethod · 0.45
EnableSynchronizationMethod · 0.45
LaunchMethod · 0.45
GetHandleMethod · 0.45

Tested by

no test coverage detected