~ubuntu-branches/ubuntu/utopic/nordugrid-arc/utopic

« back to all changes in this revision

Viewing changes to src/hed/acc/JobDescriptionParser/ADLParser.cpp

  • Committer: Package Import Robot
  • Author(s): Mattias Ellert
  • Date: 2014-05-01 20:51:02 UTC
  • mfrom: (1.1.11)
  • Revision ID: package-import@ubuntu.com-20140501205102-icy9t3348uxobyx7
Tags: 4.1.0-1
* 4.1.0 Release
* Call dh_autoreconf to support ppc64le (Closes: #744639)

Show diffs side-by-side

added added

removed removed

Lines of Context:
18
18
 
19
19
namespace Arc {
20
20
 
 
21
  /// \mapname ADL EMI ADL
 
22
  /// The libarccompute library has almost full support for EMI Activity
 
23
  /// Description Language (ADL) v1.16, it is described in the EMI Execution
 
24
  /// Service (ES) specification
 
25
  /// (<a href="https://twiki.cern.ch/twiki/pub/EMI/EmiExecutionService/EMI-ES-Specification_v1.16.odt">EMI-ES-Specification_v1.16.odt</a>).<br/>
 
26
  /// Currently the ADL parser is not able to parse: <br/>
 
27
  /// TODO
21
28
  ADLParser::ADLParser(PluginArgument* parg)
22
29
    : JobDescriptionParserPlugin(parg) {
23
30
    supportedLanguages.push_back("emies:adl");
29
36
    return new ADLParser(arg);
30
37
  }
31
38
 
32
 
  //  EMI state             ARC state
 
39
  // EMI state             ARC state
33
40
  // ACCEPTED              ACCEPTED
34
41
  // PREPROCESSING         PREPARING
35
42
  //                       SUBMIT
349
356
    XMLNode staging = node["adl:DataStaging"];
350
357
 
351
358
    if((bool)identification) {
 
359
      /// \mapattr ActivityIdentification.Name -> JobName
352
360
      job.Identification.JobName = (std::string)identification["adl:Name"];
 
361
      /// \mapattr ActivityIdentification.Description -> Description
353
362
      job.Identification.Description = (std::string)identification["adl:Description"];
 
363
      /// \mapattr ActivityIdentification.Type -> JobIdentificationType::Type
354
364
      job.Identification.Type = (std::string)identification["adl:Type"];
 
365
      /// \mapattr ActivityIdentification.Annotation -> Annotation
355
366
      for(XMLNode annotation = identification["adl:Annotation"];
356
367
                                      (bool)annotation;++annotation) {
357
368
        job.Identification.Annotation.push_back((std::string)annotation);
358
369
      }
359
370
      // ARC extension: ActivityOldID
 
371
      // TODO: Add note about this being a ARC extension.
 
372
      /// \mapattr ActivityIdentification.ActivityOldID -> ActivityOldID
360
373
      for(XMLNode activityoldid = identification["nordugrid-adl:ActivityOldID"];
361
374
                                      (bool)activityoldid;++activityoldid) {
362
375
        job.Identification.ActivityOldID.push_back((std::string)activityoldid);
363
376
      }
364
377
    }
365
378
    if((bool)application) {
 
379
      /// \mapattr Application.Executable.Path -> ExecutableType::Path
 
380
      /// \mapattr Application.Executable.Argument -> ExecutableType::Argument
366
381
      XMLNode executable = application["adl:Executable"];
367
382
      if(executable && !ParseExecutable(executable, job.Application.Executable, dialect, logger)) {
368
383
        jobdescs.clear();
369
384
        return false;
370
385
      }
 
386
      /// \mapattr Application.Input -> Input
371
387
      job.Application.Input = (std::string)application["adl:Input"];
 
388
      /// \mapattr Application.Output -> Output
372
389
      job.Application.Output = (std::string)application["adl:Output"];
 
390
      /// \mapattr Application.Error -> Error
373
391
      job.Application.Error = (std::string)application["adl:Error"];
 
392
      /// \mapattr Application.Environment -> Environment
374
393
      for(XMLNode environment = application["adl:Environment"];
375
394
                         (bool)environment;++environment) {
376
395
        job.Application.Environment.push_back(
378
397
                        (std::string)environment["adl:Name"],
379
398
                        (std::string)environment["adl:Value"]));
380
399
      }
 
400
      /// \mapattr Application.PreExecutable -> PreExecutable
381
401
      for(XMLNode preexecutable = application["adl:PreExecutable"];
382
402
          (bool)preexecutable;++preexecutable) {
383
403
        ExecutableType exec;
387
407
        }
388
408
        job.Application.PreExecutable.push_back(exec);
389
409
      }
 
410
      /// \mapattr Application.PostExecutable -> PostExecutable
390
411
      for(XMLNode postexecutable = application["adl:PostExecutable"];
391
412
          (bool)postexecutable;++postexecutable) {
392
413
        ExecutableType exec;
396
417
        }
397
418
        job.Application.PostExecutable.push_back(exec);
398
419
      }
 
420
      /// \mapattr Application.LoggingDirectory -> LogDir
399
421
      job.Application.LogDir = (std::string)application["LoggingDirectory"];
400
422
      for(XMLNode logging = application["adl:RemoteLogging"];
401
423
                                (bool)logging;++logging) {
413
435
          return false;
414
436
        }
415
437
      }
 
438
      /// \mapattr Application.ExpirationTime -> ExpirationTime
416
439
      XMLNode expire =  application["adl:ExpirationTime"];
417
440
      if((bool)expire) {
418
441
        bool b;
429
452
          }
430
453
        }
431
454
      }
 
455
      /// \mapattr Application.WipeTime -> SessionLifeTime
432
456
      XMLNode wipe =  application["adl:WipeTime"];
433
457
      if((bool)wipe) {
434
458
        job.Resources.SessionLifeTime = (std::string)wipe;
478
502
      }
479
503
    }
480
504
    if((bool)resources) {
 
505
      /// \mapattr Resources.OperatingSystem -> OperatingSystem
481
506
      XMLNode os = resources["adl:OperatingSystem"];
482
507
      if((bool)os) {
483
508
        // TODO: convert from EMI ES types. So far they look similar.
484
509
        Software os_((std::string)os["adl:Family"],(std::string)os["adl:Name"],(std::string)os["adl:Version"]);
485
510
        job.Resources.OperatingSystem.add(os_, Software::EQUAL);
486
511
      }
 
512
      /// \mapattr Resources.Platform -> Platform
487
513
      XMLNode platform = resources["adl:Platform"];
488
514
      if((bool)platform) {
489
515
        // TODO: convert from EMI ES types. So far they look similar.
490
516
        job.Resources.Platform = (std::string)platform;
491
517
      }
 
518
      /// \mapattr Resources.RuntimeEnvironment -> RunTimeEnvironment
492
519
      for(XMLNode rte = resources["adl:RuntimeEnvironment"];(bool)rte;++rte) {
493
520
        Software rte_("",(std::string)rte["adl:Name"],(std::string)rte["adl:Version"]);
494
521
        for(XMLNode o = rte["adl:Option"];(bool)o;++o) {
504
531
      if((bool)resources["adl:ParallelEnvironment"]) {
505
532
        ParallelEnvironmentType& pe = job.Resources.ParallelEnvironment;
506
533
        XMLNode xpe = resources["adl:ParallelEnvironment"];
 
534
        /// \mapattr Resources.ParallelEnvironment.Type ->  ParallelEnvironmentType::Type
507
535
        if ((bool)xpe["adl:Type"]) {
508
536
          pe.Type = (std::string)xpe["adl:Type"];
509
537
        }
 
538
        /// \mapattr Resources.ParallelEnvironment.Version ->  ParallelEnvironmentType::Version
510
539
        if ((bool)xpe["adl:Version"]) {
511
540
          pe.Version = (std::string)xpe["adl:Version"];
512
541
        }
 
542
        /// \mapattr Resources.ParallelEnvironment.ProcessesPerSlot ->  ParallelEnvironmentType::ProcessesPerSlot
513
543
        if (((bool)xpe["adl:ProcessesPerSlot"]) && !stringto(xpe["adl:ProcessesPerSlot"], pe.ProcessesPerSlot)) {
514
544
          logger.msg(ERROR, "[ADLParser] Missing or wrong value in ProcessesPerSlot.");
515
545
          jobdescs.clear();
516
546
          return false;
517
547
        }
 
548
        /// \mapattr Resources.ParallelEnvironment.ThreadsPerProcess ->  ParallelEnvironmentType::ThreadsPerProcess
518
549
        if (((bool)xpe["adl:ThreadsPerProcess"]) && !stringto(xpe["adl:ThreadsPerProcess"], pe.ThreadsPerProcess)) {
519
550
          logger.msg(ERROR, "[ADLParser] Missing or wrong value in ThreadsPerProcess.");
520
551
          jobdescs.clear();
521
552
          return false;
522
553
        }
 
554
        /// \mapattr Resources.ParallelEnvironment.Option ->  ParallelEnvironmentType::Options
523
555
        for (XMLNode xOption = xpe["adl:Option"]; xOption; ++xOption) {
524
556
          if ((!(bool)xOption["adl:Name"]) || ((std::string)xOption["adl:Name"]).empty()) {
525
557
            logger.msg(ERROR, "[ADLParser] Missing Name element or value in ParallelEnvironment/Option element.");
529
561
          pe.Options.insert(std::make_pair<std::string, std::string>(xOption["adl:Name"], xOption["adl:Value"]));
530
562
        }
531
563
      }
 
564
      /// \mapattr Resources.Coprocessor -> Coprocessor
532
565
      XMLNode coprocessor = resources["adl:Coprocessor"];
533
566
      if((bool)coprocessor && !((std::string)coprocessor).empty()) {
534
567
        job.Resources.Coprocessor = coprocessor;
537
570
          return false;
538
571
        }
539
572
      }
 
573
      /// \mapattr Resources.NetworkInfo -> NetworkInfo
540
574
      XMLNode netinfo = resources["adl:NetworkInfo"];
541
575
      if(((bool)netinfo)) {
542
576
        logger.msg(ERROR, "[ADLParser] NetworkInfo is not supported yet.");
543
577
        jobdescs.clear();
544
578
        return false;
545
579
      }
 
580
      /// \mapattr Resources.NodeAccess -> NodeAccess
546
581
      XMLNode nodeaccess = resources["adl:NodeAccess"];
547
582
      if(nodeaccess) {
548
583
        std::string na = nodeaccess;
560
595
      }
561
596
      XMLNode slot = resources["adl:SlotRequirement"];
562
597
      if((bool)slot) {
 
598
        /// \mapattr Resources.SlotRequirement.NumberOfSlots -> NumberOfSlots
563
599
        if(!stringto(slot["adl:NumberOfSlots"],job.Resources.SlotRequirement.NumberOfSlots)) {
564
600
          logger.msg(ERROR, "[ADLParser] Missing or wrong value in NumberOfSlots.");
565
601
          jobdescs.clear();
574
610
            }
575
611
            job.Resources.SlotRequirement.SlotsPerHost = job.Resources.SlotRequirement.NumberOfSlots;
576
612
          }
 
613
          /// \mapattr Resources.SlotRequirement.SlotsPerHost -> SlotsPerHost
577
614
          else if(!stringto(slot["adl:SlotsPerHost"],job.Resources.SlotRequirement.SlotsPerHost)) {
578
615
            logger.msg(ERROR, "[ADLParser] Missing or wrong value in SlotsPerHost.");
579
616
            jobdescs.clear();
580
617
            return false;
581
618
          }
 
619
          /// \mapattr Resources.SlotRequirement.ExclusiveExecution -> ExclusiveExecution
582
620
          if((bool)slot["adl:ExclusiveExecution"]) {
583
621
            const std::string ee = slot["adl:ExclusiveExecution"];
584
622
            if ((ee == "true") || (ee == "1")) {
593
631
          }
594
632
        }
595
633
      }
 
634
      /// \mapattr Resources.QueueName -> QueueName
596
635
      XMLNode queue = resources["adl:QueueName"];
597
636
      if((bool)queue) {
598
637
        job.Resources.QueueName = (std::string)queue;
599
638
      }
 
639
      /// \mapattr Resources.IndividualPhysicalMemory -> IndividualPhysicalMemory
600
640
      XMLNode memory;
601
641
      memory = resources["adl:IndividualPhysicalMemory"];
602
642
      if((bool)memory) {
606
646
          return false;
607
647
        }
608
648
      }
 
649
      /// \mapattr Resources.IndividualVirtualMemory -> IndividualVirtualMemory
609
650
      memory = resources["adl:IndividualVirtualMemory"];
610
651
      if((bool)memory) {
611
652
        if(!stringto((std::string)memory,job.Resources.IndividualVirtualMemory.max)) {
614
655
          return false;
615
656
        }
616
657
      }
 
658
      /// \mapattr Resources.DiskSpaceRequirement -> DiskSpace
617
659
      memory = resources["adl:DiskSpaceRequirement"];
618
660
      if((bool)memory) {
619
661
        unsigned long long int v = 0;
624
666
        }
625
667
        job.Resources.DiskSpaceRequirement.DiskSpace.min = (v - 1) / 1024*1024 + 1;
626
668
      }
 
669
      /// \mapattr Resources.RemoteSessionAccess -> SessionDirectoryAccess
627
670
      if((bool)resources["adl:RemoteSessionAccess"]) {
628
671
        bool v = false;
629
672
        if(!ParseFlag(resources["adl:RemoteSessionAccess"],v,logger)) {
640
683
      XMLNode time;
641
684
      time = resources["adl:IndividualCPUTime"];
642
685
      if((bool)time) {
 
686
        /// \mapattr Resources.IndividualCPUTime -> IndividualCPUTime
643
687
        if(!stringto((std::string)time,job.Resources.IndividualCPUTime.range.max)) {
644
688
          logger.msg(ERROR, "[ADLParser] Missing or wrong value in IndividualCPUTime.");
645
689
          jobdescs.clear();
648
692
      }
649
693
      time = resources["adl:TotalCPUTime"];
650
694
      if((bool)time) {
 
695
        /// \mapattr Resources.TotalCPUTime -> TotalCPUTime
651
696
        if(!stringto((std::string)time,job.Resources.TotalCPUTime.range.max)) {
652
697
          logger.msg(ERROR, "[ADLParser] Missing or wrong value in TotalCPUTime.");
653
698
          jobdescs.clear();
656
701
      }
657
702
      time = resources["adl:WallTime"];
658
703
      if((bool)time) {
 
704
        /// \mapattr Resources.WallTime -> IndividualWallTime
 
705
        /// TODO: Change to IndividualWallTime
659
706
        if(!stringto((std::string)time,job.Resources.TotalWallTime.range.max)) {
660
707
          logger.msg(ERROR, "[ADLParser] Missing or wrong value in WallTime.");
661
708
          jobdescs.clear();
807
854
    XMLNode staging = description.NewChild("DataStaging");
808
855
 
809
856
    // ActivityIdentification
 
857
    /// \mapattr ActivityIdentification.JobName <- JobName
810
858
    if(!job.Identification.JobName.empty()) identification.NewChild("Name") = job.Identification.JobName;
 
859
    /// \mapattr ActivityIdentification.Description <- Description
811
860
    if(!job.Identification.Description.empty()) identification.NewChild("Description") = job.Identification.Description;
 
861
    /// \mapattr ActivityIdentification.Type <- JobIdentificationType::Type
812
862
    if(!job.Identification.Type.empty()) identification.NewChild("Type") = job.Identification.Type;
 
863
    /// \mapattr ActivityIdentification.Annotation <- Annotation
813
864
    for (std::list<std::string>::const_iterator it = job.Identification.Annotation.begin();
814
865
         it != job.Identification.Annotation.end(); it++) {
815
866
      identification.NewChild("Annotation") = *it;
816
867
    }
817
868
    // ARC extension: ActivityOldID
 
869
    /// \mapattr ActivityIdentification.ActivityOldID <- ActivityOldID
 
870
    /// TODO: Add mapping note that this element is an extention.
818
871
    for (std::list<std::string>::const_iterator it = job.Identification.ActivityOldID.begin();
819
872
         it != job.Identification.ActivityOldID.end(); ++it) {
820
873
      identification.NewChild("nordugrid-adl:ActivityOldID") = *it;
821
874
    }
822
875
 
823
876
    // Application
 
877
    /// \mapattr Application.Executable.Path <- ExecutableType::Path
 
878
    /// \mapattr Application.Executable.Argument <- ExecutableType::Argument
824
879
    generateExecutableTypeElement(application.NewChild("Executable"), job.Application.Executable);
 
880
    /// \mapattr Application.Input <- Input
825
881
    if(!job.Application.Input.empty()) application.NewChild("Input") = job.Application.Input;
 
882
    /// \mapattr Application.Output <- Output
826
883
    if(!job.Application.Output.empty()) application.NewChild("Output") = job.Application.Output;
 
884
    /// \mapattr Application.Error <- Error
827
885
    if(!job.Application.Error.empty()) application.NewChild("Error") = job.Application.Error;
 
886
    /// \mapattr Application.Environment <- Environment
828
887
    for(std::list< std::pair<std::string, std::string> >::const_iterator it =
829
888
        job.Application.Environment.begin(); it != job.Application.Environment.end(); it++) {
830
889
      XMLNode environment = application.NewChild("Environment");
831
890
      environment.NewChild("Name") = it->first;
832
891
      environment.NewChild("Value") = it->second;
833
892
    }
 
893
    /// \mapattr Application.PreExecutable <- PreExecutable
834
894
    for(std::list<ExecutableType>::const_iterator it = job.Application.PreExecutable.begin();
835
895
        it != job.Application.PreExecutable.end(); ++it) {
836
896
      generateExecutableTypeElement(application.NewChild("PreExecutable"), *it);
837
897
    }
 
898
    /// \mapattr Application.PostExecutable <- PostExecutable
838
899
    for(std::list<ExecutableType>::const_iterator it = job.Application.PostExecutable.begin();
839
900
        it != job.Application.PostExecutable.end(); ++it) {
840
901
      generateExecutableTypeElement(application.NewChild("PostExecutable"), *it);
841
902
    }
 
903
    /// \mapattr Application.LoggingDirectory <- LogDir
842
904
    if(!job.Application.LogDir.empty()) application.NewChild("LoggingDirectory") = job.Application.LogDir;
843
905
    for (std::list<RemoteLoggingType>::const_iterator it = job.Application.RemoteLogging.begin();
844
906
         it != job.Application.RemoteLogging.end(); it++) {
847
909
      logging.NewChild("URL") = it->Location.fullstr();
848
910
      if(it->optional) logging.NewAttribute("optional") = "true";
849
911
    }
 
912
    /// \mapattr Application.ExpirationTime <- ExpirationTime
850
913
    if(job.Application.ExpirationTime > -1) {
851
914
      XMLNode expire = application.NewChild("ExpirationTime");
852
915
      expire = job.Application.ExpirationTime.str();
853
916
      //if() expire.NewAttribute("optional") = "true";
854
917
    }
 
918
    /// \mapattr Application.WipeTime <- SessionLifeTime
855
919
    if(job.Resources.SessionLifeTime > -1) {
856
920
      XMLNode wipe = application.NewChild("WipeTime");
857
921
      // TODO: ask for type change from dateTime to period.
858
922
      wipe = (std::string)job.Resources.SessionLifeTime;
859
923
      //if() wipe.NewAttribute("optional") = "true";
860
924
    }
 
925
    
861
926
    for (std::list<NotificationType>::const_iterator it = job.Application.Notification.begin();
862
927
         it != job.Application.Notification.end(); it++) {
863
928
      XMLNode notification = application.NewChild("Notification");
866
931
      for (std::list<std::string>::const_iterator s = it->States.begin();
867
932
                  s != it->States.end(); s++) {
868
933
        std::string st = InternalStateToADL(*s,false,logger);
869
 
                if(st.empty()) continue; // return false; TODO later
870
 
                notification.NewChild("OnState") = st;
871
 
              }
872
 
            }
873
 
            // job.Application.Rerun
874
 
            // job.Application.Priority
875
 
            // job.Application.ProcessingStartTime
876
 
            // job.Application.AccessControl
877
 
            // job.Application.CredentialService
878
 
            // job.Application.DryRun
879
 
 
880
 
            // Resources
881
 
 
882
 
            for(std::list<Software>::const_iterator o =
883
 
                                    job.Resources.OperatingSystem.getSoftwareList().begin();
884
 
                                    o != job.Resources.OperatingSystem.getSoftwareList().end(); ++o) {
885
 
              XMLNode os = resources.NewChild("OperatingSystem");
886
 
              os.NewChild("Name") = o->getName();
887
 
              std::string fam = o->getFamily();
888
 
              if(!fam.empty()) os.NewChild("Family") = fam;
 
934
        if(st.empty()) continue; // return false; TODO later
 
935
        notification.NewChild("OnState") = st;
 
936
      }
 
937
    }
 
938
    // job.Application.Rerun
 
939
    // job.Application.Priority
 
940
    // job.Application.ProcessingStartTime
 
941
    // job.Application.AccessControl
 
942
    // job.Application.CredentialService
 
943
    // job.Application.DryRun
 
944
  
 
945
    // Resources
 
946
    /// \mapattr Resources.OperatingSystem <- OperatingSystem
 
947
    for(std::list<Software>::const_iterator o = job.Resources.OperatingSystem.getSoftwareList().begin();
 
948
        o != job.Resources.OperatingSystem.getSoftwareList().end(); ++o) {
 
949
      XMLNode os = resources.NewChild("OperatingSystem");
 
950
      os.NewChild("Name") = o->getName();
 
951
      std::string fam = o->getFamily();
 
952
      if(!fam.empty()) os.NewChild("Family") = fam;
889
953
      os.NewChild("Version") = o->getVersion();
890
954
    }
 
955
    /// \mapattr Resources.Platform <- Platform
891
956
    if(!job.Resources.Platform.empty()) {
892
957
      // TODO: convert to EMI ES types. So far they look same.
893
958
      resources.NewChild("Platform") = job.Resources.Platform;
894
959
    }
 
960
    /// \mapattr Resources.RuntimeEnvironment <- RunTimeEnvironment
895
961
    for(std::list<Software>::const_iterator s =
896
962
                    job.Resources.RunTimeEnvironment.getSoftwareList().begin();
897
963
                    s != job.Resources.RunTimeEnvironment.getSoftwareList().end();++s) {
907
973
    {
908
974
      XMLNode xpe("<ParallelEnvironment/>");
909
975
      const ParallelEnvironmentType& pe = job.Resources.ParallelEnvironment;
 
976
      /// \mapattr Resources.ParallelEnvironment.Type <- ParallelEnvironmentType::Type
910
977
      if (!pe.Type.empty()) {
911
978
        xpe.NewChild("Type") = pe.Type;
912
979
      }
 
980
      /// \mapattr Resources.ParallelEnvironment.Version <- ParallelEnvironmentType::Version
913
981
      if (!pe.Version.empty()) {
914
982
        xpe.NewChild("Version") = pe.Version;
915
983
      }
 
984
      /// \mapattr Resources.ParallelEnvironment.ProcessesPerSlot <- ParallelEnvironmentType::ProcessesPerSlot
916
985
      if (pe.ProcessesPerSlot > -1) {
917
986
        xpe.NewChild("ProcessesPerSlot") = tostring(pe.ProcessesPerSlot);
918
987
      }
 
988
      /// \mapattr Resources.ParallelEnvironment.ThreadsPerProcess <- ParallelEnvironmentType::ThreadsPerProcess
919
989
      if (pe.ThreadsPerProcess > -1) {
920
990
        xpe.NewChild("ThreadsPerProcess") = tostring(pe.ThreadsPerProcess);
921
991
      }
 
992
      /// \mapattr Resources.ParallelEnvironment.Option <- ParallelEnvironmentType::Options
922
993
      for (std::multimap<std::string, std::string>::const_iterator it = pe.Options.begin();
923
994
           it != pe.Options.end(); ++it) {
924
995
        XMLNode xo = xpe.NewChild("Option");
929
1000
        resources.NewChild(xpe);
930
1001
      }
931
1002
    }
 
1003
    /// \mapattr Resources.Coprocessor <- Coprocessor
932
1004
    if(!((std::string)job.Resources.Coprocessor).empty()) {
933
1005
      XMLNode coprocessor = resources.NewChild("Coprocessor");
934
1006
      coprocessor = (std::string)job.Resources.Coprocessor;
935
1007
      if(job.Resources.Coprocessor.optIn) coprocessor.NewAttribute("optional") = "true";
936
1008
    }
937
1009
    //TODO: check values. So far they look close. 
 
1010
    /// \mapattr Resources.NetworkInfo <- NetworkInfo
938
1011
    if(!job.Resources.NetworkInfo.empty()) {
939
1012
      resources.NewChild("NetworkInfo") = job.Resources.NetworkInfo;
940
1013
    }
 
1014
    /// \mapattr Resources.NodeAccess <- NodeAccess
941
1015
    switch(job.Resources.NodeAccess) {
942
1016
      case NAT_INBOUND: resources.NewChild("NodeAccess") = "inbound"; break;
943
1017
      case NAT_OUTBOUND: resources.NewChild("NodeAccess") = "outbound"; break;
944
1018
      case NAT_INOUTBOUND: resources.NewChild("NodeAccess") = "inoutbound"; break;
945
1019
      default: break;
946
1020
    }
 
1021
    /// \mapattr Resources.IndividualPhysicalMemory <- IndividualPhysicalMemory
947
1022
    if(job.Resources.IndividualPhysicalMemory.max != -1) {
948
1023
      resources.NewChild("IndividualPhysicalMemory") = tostring(job.Resources.IndividualPhysicalMemory.max);
949
1024
    }
 
1025
    /// \mapattr Resources.IndividualVirtualMemory <- IndividualVirtualMemory
950
1026
    if(job.Resources.IndividualVirtualMemory.max != -1) {
951
1027
      resources.NewChild("IndividualVirtualMemory") = tostring(job.Resources.IndividualVirtualMemory.max);
952
1028
    }
 
1029
    /// \mapattr Resources.DiskSpaceRequirement <- DiskSpace
953
1030
    if(job.Resources.DiskSpaceRequirement.DiskSpace.min > -1) {
954
1031
      resources.NewChild("DiskSpaceRequirement") = tostring(job.Resources.DiskSpaceRequirement.DiskSpace.min*1024*1024);
955
1032
    }
 
1033
    /// \mapattr Resources.RemoteSessionAccess <- SessionDirectoryAccess
956
1034
    switch(job.Resources.SessionDirectoryAccess) {
957
1035
      case SDAM_RW: resources.NewChild("RemoteSessionAccess") = "true"; break;
958
 
      case SDAM_RO: resources.NewChild("RemoteSessionAccess") = "true"; break; // approximately
 
1036
      case SDAM_RO: resources.NewChild("RemoteSessionAccess") = "true"; break; // approximately; TODO: Document in mapping.
959
1037
      default: break;
960
1038
    }
961
1039
    //Benchmark
962
1040
    //  BenchmarkType
963
1041
    //  BenchmarkValue
964
1042
    XMLNode slot = resources.NewChild("SlotRequirement");
 
1043
    /// \mapattr Resources.SlotRequirement.NumberOfSlots <- NumberOfSlots
965
1044
    if(job.Resources.SlotRequirement.NumberOfSlots > -1) {
966
1045
      slot.NewChild("NumberOfSlots") = tostring(job.Resources.SlotRequirement.NumberOfSlots);
967
1046
    }
 
1047
    /// \mapattr Resources.SlotRequirement.SlotsPerHost <- SlotsPerHost
968
1048
    if (job.Resources.SlotRequirement.SlotsPerHost > -1) {
969
1049
      slot.NewChild("SlotsPerHost") = tostring(job.Resources.SlotRequirement.SlotsPerHost);
970
1050
    }
 
1051
    /// \mapattr Resources.SlotRequirement.ExclusiveExecution <- ExclusiveExecution
971
1052
    switch(job.Resources.SlotRequirement.ExclusiveExecution) {
972
1053
      case SlotRequirementType::EE_TRUE: slot.NewChild("ExclusiveExecution") = "true"; break;
973
1054
      case SlotRequirementType::EE_FALSE: slot.NewChild("ExclusiveExecution") = "false"; break;
974
1055
      default: break;
975
1056
    }
976
1057
    if(slot.Size() <= 0) slot.Destroy();
 
1058
    /// \mapattr Resources.QueueName <- QueueName
977
1059
    if(!job.Resources.QueueName.empty()) {;
978
1060
      resources.NewChild("QueueName") = job.Resources.QueueName;
979
1061
    }
 
1062
    /// \mapattr Resources.IndividualCPUTime <- IndividualCPUTime
980
1063
    if(job.Resources.IndividualCPUTime.range.max != -1) {
981
1064
      resources.NewChild("IndividualCPUTime") = tostring(job.Resources.IndividualCPUTime.range.max);
982
1065
    }
 
1066
    /// \mapattr Resources.TotalCPUTime <- TotalCPUTime
983
1067
    if(job.Resources.TotalCPUTime.range.max != -1) {
984
1068
      resources.NewChild("TotalCPUTime") = tostring(job.Resources.TotalCPUTime.range.max);
985
1069
    }
 
1070
    /// \mapattr Resources.WallTime <- IndividualWallTime
986
1071
    if(job.Resources.TotalWallTime.range.max != -1) {
987
1072
      resources.NewChild("WallTime") = tostring(job.Resources.TotalWallTime.range.max);
988
1073
    } else if(job.Resources.IndividualWallTime.range.max != -1) {