Exception: Syskit::DeviceAllocationFailed

Inherits:
SpecError show all
Defined in:
lib/syskit/exceptions.rb

Overview

Exception raised when we could not find devices to allocate for tasks that are device drivers

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(plan, tasks) ⇒ DeviceAllocationFailed

Returns a new instance of DeviceAllocationFailed



366
367
368
369
370
371
372
373
374
# File 'lib/syskit/exceptions.rb', line 366

def initialize(plan, tasks)
    @failed_tasks = tasks.dup
    @candidates = Hash.new
    @task_parents = Hash.new

    tasks.each do |abstract_task|
        resolve_device_task(plan, abstract_task)
    end
end

Instance Attribute Details

#candidatesObject (readonly)

Existing candidates for this device



364
365
366
# File 'lib/syskit/exceptions.rb', line 364

def candidates
  @candidates
end

#failed_tasksObject (readonly)

The set of tasks that failed allocation



359
360
361
# File 'lib/syskit/exceptions.rb', line 359

def failed_tasks
  @failed_tasks
end

#task_parentsObject (readonly)

A task to parents mapping for tasks involved in this error, at the time of the exception creation



362
363
364
# File 'lib/syskit/exceptions.rb', line 362

def task_parents
  @task_parents
end

Instance Method Details

#pretty_print(pp) ⇒ Object



403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
# File 'lib/syskit/exceptions.rb', line 403

def pretty_print(pp)
    pp.text "cannot find a device to tie to #{failed_tasks.size} task(s)"

    failed_tasks.each do |task|
        parents = task_parents[task]
        candidates = self.candidates[task]

        pp.breakable
        pp.text "for #{task.to_s.gsub(/Syskit::/, '')}"
        pp.nest(2) do
            if !parents.empty?
                pp.breakable
                pp.seplist(parents) do |parent|
                    role, parent = parent
                    pp.text "child #{role.to_a.first} of #{parent.to_s.gsub(/Syskit::/, '')}"
                end
            end

            pp.breakable
            pp.seplist(candidates) do |cand|
                srv, tasks = *cand
                if tasks.empty?
                    pp.text "no candidates for #{srv.short_name}"
                else
                    pp.text "candidates for #{srv.short_name}"
                    pp.nest(2) do
                        pp.breakable
                        pp.seplist(tasks) do |cand_t|
                            pp.text "#{cand_t}"
                        end
                    end
                end
            end
        end
    end
end

#resolve_device_task(plan, abstract_task) ⇒ Object



376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
# File 'lib/syskit/exceptions.rb', line 376

def resolve_device_task(plan, abstract_task)
    all_tasks = [abstract_task].to_set

    # List the possible candidates for the missing devices
    candidates = Hash.new
    abstract_task.model.each_master_driver_service do |srv|
        if !abstract_task.arguments[:"#{srv.name}_dev"]
            candidates[srv] = plan.find_local_tasks(srv.model).to_set
            candidates[srv].delete(abstract_task)
            all_tasks |= candidates[srv]
        end
    end
    self.candidates[abstract_task] = candidates

    all_tasks.each do |t|
        next if task_parents.has_key?(t)

        parents = t.
            enum_for(:each_parent_object, Roby::TaskStructure::Dependency).
            map do |parent_task|
                options = parent_task[t, Roby::TaskStructure::Dependency]
                [options[:roles], parent_task]
            end
        task_parents[t] = parents
    end
end