Show
Ignore:
Timestamp:
01/31/06 12:32:34 (18 years ago)
Author:
jerome
Message:

Introduced the 'preaccounter' directive.

Location:
pykota/trunk/pykota/accounters
Files:
2 modified

Legend:

Unmodified
Added
Removed
  • pykota/trunk/pykota/accounters/hardware.py

    r2622 r2635  
    3131 
    3232class Accounter(AccounterBase) : 
    33     def __init__(self, kotabackend, arguments) : 
     33    def __init__(self, kotabackend, arguments, ispreaccounter=0) : 
    3434        """Initializes querying accounter.""" 
    3535        AccounterBase.__init__(self, kotabackend, arguments) 
  • pykota/trunk/pykota/accounters/software.py

    r2622 r2635  
    3030    def computeJobSize(self) :     
    3131        """Feeds an external command with our datas to let it compute the job size, and return its value.""" 
     32        if (not self.isPreAccounter) and \ 
     33            (self.filter.accounter.arguments == self.filter.preaccounter.arguments) : 
     34            # if precomputing has been done and both accounter and preaccounter are 
     35            # configured the same, no need to launch a second pass since we already 
     36            # know the result. 
     37            self.filter.logdebug("Precomputing pass told us that job is %s pages long." % self.filter.softwareJobSize) 
     38            return self.filter.softwareJobSize   # Optimize : already computed ! 
     39             
     40        if self.arguments : 
     41            self.filter.logdebug("Using external script %s to compute job's size." % self.arguments) 
     42            return self.withExternalScript() 
     43        else :     
     44            self.filter.logdebug("Using internal parser to compute job's size.") 
     45            return self.withInternalParser() 
     46         
     47    def withInternalParser(self) :     
     48        """Does software accounting through an external script.""" 
     49        jobsize = 0 
     50        if self.filter.JobSizeBytes : 
     51            try : 
     52                from pkpgpdls import analyzer, pdlparser 
     53            except ImportError :     
     54                self.filter.printInfo("pkpgcounter is now distributed separately, please grab it from http://www.librelogiciel.com/software/pkpgcounter/action_Download", "error") 
     55                self.filter.printInfo("Precomputed job size will be forced to 0 pages.", "error") 
     56            else :      
     57                infile = open(self.filter.DataFile, "rb") 
     58                try : 
     59                    parser = analyzer.PDLAnalyzer(infile) 
     60                    jobsize = parser.getJobSize() 
     61                except pdlparser.PDLParserError, msg :     
     62                    # Here we just log the failure, but 
     63                    # we finally ignore it and return 0 since this 
     64                    # computation is just an indication of what the 
     65                    # job's size MAY be. 
     66                    self.filter.printInfo(_("Unable to precompute the job's size with the generic PDL analyzer : %s") % msg, "warn") 
     67                else :     
     68                    if self.filter.InputFile is not None : 
     69                        # when a filename is passed as an argument, the backend  
     70                        # must generate the correct number of copies. 
     71                        jobsize *= self.filter.Copies 
     72                infile.close()         
     73        return jobsize         
     74                 
     75    def withExternalScript(self) :     
     76        """Does software accounting through an external script.""" 
    3277        self.filter.printInfo(_("Launching SOFTWARE(%s)...") % self.arguments) 
    33         if not self.arguments : 
    34             pagecounter = self.filter.softwareJobSize   # Optimize : already computed ! 
    35             self.filter.logdebug("Internal software accounter said job is %s pages long." % repr(pagecounter)) 
    36         else : 
    37             MEGABYTE = 1024*1024 
    38             infile = open(self.filter.DataFile, "rb") 
    39             child = popen2.Popen4(self.arguments) 
    40             try : 
    41                 data = infile.read(MEGABYTE)     
    42                 while data : 
    43                     child.tochild.write(data) 
    44                     data = infile.read(MEGABYTE) 
    45                 child.tochild.flush() 
    46                 child.tochild.close()     
    47             except (IOError, OSError), msg :     
    48                 msg = "%s : %s" % (self.arguments, msg)  
    49                 self.filter.printInfo(_("Unable to compute job size with accounter %s") % msg) 
    50             infile.close() 
    51             pagecounter = None 
    52             try : 
    53                 answer = child.fromchild.read() 
    54             except (IOError, OSError), msg :     
    55                 msg = "%s : %s" % (self.arguments, msg)  
    56                 self.filter.printInfo(_("Unable to compute job size with accounter %s") % msg) 
    57             else :     
    58                 lines = [l.strip() for l in answer.split("\n")] 
    59                 for i in range(len(lines)) :  
    60                     try : 
    61                         pagecounter = int(lines[i]) 
    62                     except (AttributeError, ValueError) : 
    63                         self.filter.printInfo(_("Line [%s] skipped in accounter's output. Trying again...") % lines[i]) 
    64                     else :     
    65                         break 
    66             child.fromchild.close() 
     78        MEGABYTE = 1024*1024 
     79        infile = open(self.filter.DataFile, "rb") 
     80        child = popen2.Popen4(self.arguments) 
     81        try : 
     82            data = infile.read(MEGABYTE)     
     83            while data : 
     84                child.tochild.write(data) 
     85                data = infile.read(MEGABYTE) 
     86            child.tochild.flush() 
     87            child.tochild.close()     
     88        except (IOError, OSError), msg :     
     89            msg = "%s : %s" % (self.arguments, msg)  
     90            self.filter.printInfo(_("Unable to compute job size with accounter %s") % msg) 
     91        infile.close() 
     92        pagecounter = None 
     93        try : 
     94            answer = child.fromchild.read() 
     95        except (IOError, OSError), msg :     
     96            msg = "%s : %s" % (self.arguments, msg)  
     97            self.filter.printInfo(_("Unable to compute job size with accounter %s") % msg) 
     98        else :     
     99            lines = [l.strip() for l in answer.split("\n")] 
     100            for i in range(len(lines)) :  
     101                try : 
     102                    pagecounter = int(lines[i]) 
     103                except (AttributeError, ValueError) : 
     104                    self.filter.printInfo(_("Line [%s] skipped in accounter's output. Trying again...") % lines[i]) 
     105                else :     
     106                    break 
     107        child.fromchild.close() 
     108         
     109        try : 
     110            status = child.wait() 
     111        except OSError, msg :     
     112            self.filter.printInfo(_("Problem while waiting for software accounter pid %s to exit : %s") % (child.pid, msg)) 
     113        else :     
     114            if os.WIFEXITED(status) : 
     115                status = os.WEXITSTATUS(status) 
     116            self.filter.printInfo(_("Software accounter %s exit code is %s") % (self.arguments, str(status))) 
    67117             
    68             try : 
    69                 status = child.wait() 
    70             except OSError, msg :     
    71                 self.filter.printInfo(_("Problem while waiting for software accounter pid %s to exit : %s") % (child.pid, msg)) 
    72             else :     
    73                 if os.WIFEXITED(status) : 
    74                     status = os.WEXITSTATUS(status) 
    75                 self.filter.printInfo(_("Software accounter %s exit code is %s") % (self.arguments, str(status))) 
    76                  
    77             if pagecounter is None :     
    78                 message = _("Unable to compute job size with accounter %s") % self.arguments 
    79                 if self.onerror == "CONTINUE" : 
    80                     self.filter.printInfo(message, "error") 
    81                 else : 
    82                     raise PyKotaAccounterError, message 
    83             self.filter.logdebug("Software accounter %s said job is %s pages long." % (self.arguments, repr(pagecounter))) 
     118        if pagecounter is None :     
     119            message = _("Unable to compute job size with accounter %s") % self.arguments 
     120            if self.onerror == "CONTINUE" : 
     121                self.filter.printInfo(message, "error") 
     122            else : 
     123                raise PyKotaAccounterError, message 
     124        self.filter.logdebug("Software accounter %s said job is %s pages long." % (self.arguments, repr(pagecounter))) 
    84125             
    85126        return pagecounter or 0