o
     bqc                     @   s   d Z ddlZddlmZmZmZmZmZ ddlm	Z	m
Z
mZmZmZ ddlmZmZmZmZmZmZmZmZ G dd deZG dd	 d	eZG d
d de	ZG dd deZG dd deZG dd deeZdS )zA Convenience Classes building on the base PMAPI extension module     N)c_intc_uintc_char_pcastPOINTER)	pmContextpmValuepmDescpmErrtimeval)PM_CONTEXT_HOSTPM_CONTEXT_ARCHIVEPM_INDOM_NULL
PM_IN_NULL
PM_ID_NULLPM_SEM_COUNTER
PM_ERR_EOLPM_TYPE_DOUBLEc                   @   s   e Zd ZdZdd ZdS )
MetricCorea  
    Core metric information that can be queried from the PMAPI
    PMAPI metrics are unique by name, and MetricCores should be also
    rarely, some PMAPI metrics with different names might have identical PMIDs
    PMAPI metrics are unique by (name) and by (name,pmid) - _usually_ by (pmid)
    too.  Note that names here (and only here) are stored as byte strings for
    direct PMAPI access.  All dictionaries/caching strategies built using the
    core structure use native strings (i.e., not byte strings in python3).
    c                 C   s<   || _ t|ts|d}|| _|| _d | _d | _d | _d S )Nutf-8)	ctx
isinstancebytesencodenamepmiddesctexthelp)selfr   r   r    r    */usr/lib/python3/dist-packages/pcp/pmcc.py__init__+   s   


zMetricCore.__init__N)__name__
__module____qualname____doc__r"   r    r    r    r!   r       s    
r   c                   @   s  e Zd ZdZdd Zdd Zdd Zdd	 Zd
d Zdd Z	dd Z
dd Zdd Zdd Zdd Zdd Zdd Zdd Zdd Zd d! Zd"d# Zd$d% Zd&d' Zd(d) Zd*d+ Zd,d- Zd.d/ Zeed0d0d0Zeed0d0d0Zeed0d0d0Zeed0d0d0Zee	d0d0d0Z ee
d0d0d0Z!eeed0d0Z"eed0d0d0Z#eeed0d0Z$eeed0d0Z%eed0d0d0Z&eed0d0d0Z'eed0d0d0Z(eed0d0d0Z)d1d2 Z*d3d4 Z+d0S )5Metricz
    Additional metric information, such as conversion factors and values
    several instances of Metric may share a MetricCore instance
    c                 C   sL   || _ d | _d | _d | _d | _|jjj| _d | _	d | _
d | _d | _d | _d S N)_core_vset_values	_prevvset_prevValuesr   contentstype	_convType
_convUnits_errorStatus
_netValues_netPrevValues_netConvertedValues)r   corer    r    r!   r"   ?   s   
zMetric.__init__c                 C      | j jS r(   )r)   r   r   r    r    r!   _R_ctxO      zMetric._R_ctxc                 C   s   | j j S r(   )r)   r   decoder8   r    r    r!   _R_nameQ   s   zMetric._R_namec                 C   r7   r(   )r)   r   r8   r    r    r!   _R_pmidS   r:   zMetric._R_pmidc                 C   r7   r(   )r)   r   r8   r    r    r!   _R_descU   r:   zMetric._R_descc                 C   r7   r(   )r)   r   r8   r    r    r!   _R_textW   r:   zMetric._R_textc                 C   r7   r(   )r)   r   r8   r    r    r!   _R_helpY   r:   zMetric._R_helpc                 C   s   t |jjtt}|| S )z% Return the vlist[vlist_idx] of vset )r   r.   vlistr   r   )r   vset	vlist_idxlistptrr    r    r!   	get_vlist\   s   zMetric.get_vlistc                 C   s   |  ||jS )z. Return the inst for vlist[vlist_idx] of vset )rE   inst)r   rB   rC   r    r    r!   get_insta   s   zMetric.get_instc              	   C   s   |}| j }|| jjj}g }t|jD ]Q}| ||}z||j }W n t	y.   d}Y nw | j 
|j|| jj| j}	| jrWttd  }
| j|
d< | j | j|	|
d| j}	|	| j}||||f q|S )zj Extract the value for a singleton or list of instances
            as a triple (inst, name, val)
            r   )r   
mcGetInstDr   r.   indomrangenumvalrE   rF   KeyErrorpmExtractValuevalfmtr/   r0   r1   r   r	   pmConvScaledrefappend)r   inValuesrB   r   instDvalLiinstvalr   outAtomr   valuer    r    r!   computeValuese   s.   

zMetric.computeValuesc                 C   sV   ||j kr| ||}||jkr|S t|j D ]}| ||}||jkr(|  S qdS )z2 Find a metric instance in the previous resultset N)rM   rE   rF   rL   )r   indexrF   pvsetpinstvalpir    r    r!   _find_previous_instval~   s   


zMetric._find_previous_instvalc              	   C   sR  | j jtkr| |S |du rdS |}|}| j}|| j jj}g }t|j	D ]}	| 
||	}
| |	|
j|}|du r<q'z||
j }W n tyN   d}Y nw | j|j|
| j jt}| j|j|| j jt}| jrttd  }| j |d< | jt||d| j}| jt||d| j}|t}|t}||kr||
||| | f q'|S )z Extract the value for a singleton or list of instances as a
            triple (inst, name, val) for COUNTER metrics with the value
            delta calculation applied (for rate conversion).
        NrH   rI   r   )r   semr   r[   r   rJ   r.   rK   rL   rM   rE   r`   rF   rN   rO   rP   r/   r   r1   r   r	   rQ   rR   rS   )r   values
prevValuesdeltar]   rB   r   rU   rV   rW   rX   r^   r   rY   poutAtomr   rZ   pvaluer    r    r!   convertValues   sP   



zMetric.convertValuesc                 C      | j S r(   )r+   r8   r    r    r!   	_R_values      zMetric._R_valuesc                 C   rh   r(   )r-   r8   r    r    r!   _R_prevValues   rj   zMetric._R_prevValuesc                 C   rh   r(   r0   r8   r    r    r!   _R_convType   rj   zMetric._R_convTypec                 C   rh   r(   r1   r8   r    r    r!   _R_convUnits   rj   zMetric._R_convUnitsc                 C   rh   r(   )r2   r8   r    r    r!   _R_errorStatus   rj   zMetric._R_errorStatusc                 C   rh   r(   )_netConvValuesr8   r    r    r!   _R_netConvValues   rj   zMetric._R_netConvValuesc                 C      | j sd S | | j | _| jS r(   )r,   r[   r4   r8   r    r    r!   _R_netPrevValues      zMetric._R_netPrevValuesc                 C   rs   r(   )r*   r[   r3   r8   r    r    r!   _R_netValues   ru   zMetric._R_netValuesc                 C   s    | j | _|| _ | j| _d | _d S r(   )r+   _prev	_netValue_netPrev)r   rb   r    r    r!   	_W_values   s   
zMetric._W_valuesc                 C   
   || _ d S r(   rl   r   rZ   r    r    r!   _W_convType      
zMetric._W_convTypec                 C   r{   r(   rn   r|   r    r    r!   _W_convUnits   r~   zMetric._W_convUnitsNc                 C   sN   | j | jj}tdd| | j | jj}| jD ]\}}}td|| qd S )Nz   zindom:)r   
pmInDomStrr   rK   printrJ   	netValues)r   indomstr_r   valr    r    r!   metricPrint   s   zMetric.metricPrintc                 C   s   |  | j| j|}|| _| jS r(   )rg   r*   r,   rq   )r   rd   convertedListr    r    r!   metricConvert   s   zMetric.metricConvert),r#   r$   r%   r&   r"   r9   r<   r=   r>   r?   r@   rE   rG   r[   r`   rg   ri   rk   rm   ro   rp   rr   rt   rv   rz   r}   r   propertyr   r   r   r   r   r   rb   rc   convType	convUnitserrorStatusr   netPrevValuesnetConvValuesr   r   r    r    r    r!   r'   6   sR    (r'   c                   @   sF   e Zd ZdZedfddZdd Zdd Zd	d
 Zdd Z	dd Z
dS )MetricCachea}  
    A cache of MetricCores is kept to reduce calls into the PMAPI library
    this also slightly reduces the memory footprint of Metric instances
    that share a common MetricCore
    a cache of instance domain information is also kept, which further
    reduces calls into the PMAPI and reduces the memory footprint of
    Metric objects that share a common instance domain
    local:c                 C   s0   t | || i | _i | _i | _d| _d| _d S )Nr   )r   r"   	_mcIndomD
_mcByNameD
_mcByPmidD
_mcCounter
_mcMetricsr   typedtargetr    r    r!   r"     s   
zMetricCache.__init__c                 C   s
   | j | S )z/ Query the instance : instance_list dictionary )r   )r   rK   r    r    r!   rJ     s   
zMetricCache.mcGetInstDc                 C   s   |j jj}|| jvrIt|jttjkrtdi}n(| jt	kr'| 
|j \}}n| |j \}}|dur?|dur?tt||}ni }| j||i |j jjtkrW|  jd7  _|  jd7  _| j|j |i | j|j|i dS )z Update the dictionary s
   PM_IN_NULLNrI   )r   r.   rK   r   r   rZ   r   r   _typer   pmGetInDomArchive
pmGetInDomdictzipupdatera   r   r   r   r   r   r;   r   r   )r   r6   rK   instmapinstLnameLr    r    r!   _mcAdd  s    



zMetricCache._mcAddc                 C   s   g }d}d}t |D ]%\}}t|tr| }| j|}|s*|s#i }|||i || q
|r\| |	 \}}|D ]\}}	|	t
krO|sIg }|| q=| ||	}
|
||| < q=||fS )z3 Update the core (metric id, description,...) list N)	enumerater   r   r;   r   getr   rS   mcFetchPmidskeysr   _mcCreateCore)r   r   coreLmissDerrLr\   r   r6   idLr   newcorer    r    r!   mcGetCoresByName+  s,   
zMetricCache.mcGetCoresByNamec              
   C   sl   t | ||}z| ||_W n  ty. } zd| | f }tj| t	dd}~ww | 
| |S )z Update the core description z%s: pmLookupDesc: %srI   N)r   pmLookupDescr   r
   prognamemessagesysstderrwrite
SystemExitr   )r   r   r   r   errorfailr    r    r!   r   N  s   
zMetricCache._mcCreateCorec           
   
   C   s   d}t t|  }t|D ]\}}t|ts|d}t |||< qz%| |}t|t|k rFdt|t|f }tj	d|  t
dW n  tyg } zd| | f }	tj	|	 t
dd}~ww t|||fS )zD Update the core metric ids.  note: some names have identical pmids Nr   z%d of %d metric nameszCannot resolve %srI   z%s: pmLookupName: %s)r   lenr   r   r   r   pmLookupNamer   r   r   r   r
   r   r   r   )
r   r   r   nameAr\   r   	pmidArraymissingr   r   r    r    r!   r   \  s(   


zMetricCache.mcFetchPmidsN)r#   r$   r%   r&   r   r"   rJ   r   r   r   r   r    r    r    r!   r      s    #r   c                   @   s   e Zd ZdZdd Zdd Zdd Zdd	 Zd
d Zdd Z	dd Z
dd ZeedddZeedddZeedddZeeeddZeedddZee
dddZee	dddZg fddZdd Zdd Zdd Zdd ZdS )MetricGroupa  
    Manages a group of metrics for fetching the values of
    a MetricGroup is a dictionary of Metric objects, for which data can
    be fetched from a target system using a single call to pmFetch
    the Metric objects are indexed by the metric name
    pmFetch fetches data for a list of pmIDs, so there is also a shadow
    dictionary keyed by pmID, along with a shadow list of pmIDs
    c                 C   rh   r(   )_ctxr8   r    r    r!   _R_contextCache  rj   zMetricGroup._R_contextCachec                 C   s   | j j| j jkS r(   )r   r   r   r8   r    r    r!   _R_nonCounters  s   zMetricGroup._R_nonCountersc                 C   rh   r(   )
_pmidArrayr8   r    r    r!   _R_pmidArray  rj   zMetricGroup._R_pmidArrayc                 C   
   | j jjS r(   )_resultr.   	timestampr8   r    r    r!   _R_timestamp  r~   zMetricGroup._R_timestampc                 C   rh   r(   )r   r8   r    r    r!   	_R_result  rj   zMetricGroup._R_resultc                 C   r   r(   )rw   r.   r   r8   r    r    r!   _R_prevTimestamp  r~   zMetricGroup._R_prevTimestampc                 C   rh   r(   )rw   r8   r    r    r!   _R_prev  rj   zMetricGroup._R_prevc                 C   s   | j | _|| _ d S r(   )r   rw   )r   pmresultr    r    r!   	_W_result  s   
zMetricGroup._W_resultNc                 C   s6   t |  || _d | _d | _d | _i | _| | d S r(   )r   r"   r   r   r   rw   _altDmgAdd)r   contextCacheinLr    r    r!   r"     s   
zMetricGroup.__init__c                 C   *   || v rt dt| |t| |d d S Nz)metric group with that key already exists)r   rN   r   __setitem__r   r   attrrZ   r    r    r!   r        zMetricGroup.__setitem__c           	      C   s   | j |\}}|D ]}t|}| |j|i | j|j|i q
t| }t|  | _	t
|  D ]\}}t| | j| j	|< q2dS )z Create the list of Metric(s) N)r   r   r'   r   r   r   r   r   r   r   r   r   )	r   r   r   r   r6   metricnxkeyr    r    r!   r     s   zMetricGroup.mgAddc              
   C   s   z8| j | j| _| jj}t| jjjD ] }| jj|}| jj|}| j	| j
| j	| _|| j	| _
qW |jS  tyc } z|jd tkrKtdd| | f }tj| tdd}~ww )zl
        Fetch the list of Metric values.  Save the old value.
        Return the result timestamp.
        r   z%s: pmFetch: %srI   N)r   pmFetchr   resultr.   rL   numpmidget_pmidget_vsetr   r*   r,   r
   argsr   r   r   r   r   r   r   r   )r   r   rW   r   rB   r   r   r    r    r!   mgFetch  s$   zMetricGroup.mgFetchc                 C   s(   | j durt| j}nd}t| j| S )z
        Sample delta - used for rate conversion calculations, which
        requires timestamps from successive samples.
        N        )rw   floatprevTimestampr   )r   r   r    r    r!   mgDelta  s   
zMetricGroup.mgDelta)r#   r$   r%   r&   r   r   r   r   r   r   r   r   r   r   nonCountersr   r   r   prevr   r"   r   r   r   r   r    r    r    r!   r   r  s,    	r   c                   @   s    e Zd ZdZdd Zdd ZdS )MetricGroupPrintera  
    Handles reporting of MetricGroups within a GroupManager.
    This object is called upon at the end of each fetch when
    new values are available.  It is also responsible for
    producing any initial (or on-going) header information
    that the tool may wish to report.
    c                 C   s4   |  D ]}|| }|  D ]}||   qqdS )z0 Base implementation, all tools should override N)r   r   )r   manager
group_namegroupmetric_namer    r    r!   report  s   zMetricGroupPrinter.reportc                 C   s>   |  D ]}|| }| }|  D ]	}|| | qqdS )z1 Do conversion for all metrics across all groups N)r   r   r   )r   r   r   r   rd   r   r    r    r!   convert  s   zMetricGroupPrinter.convertN)r#   r$   r%   r&   r   r   r    r    r    r!   r     s    r   c                   @   s   e Zd ZdZdd Zdd Zdd Zdd	 Zd
d Zdd Z	dd Z
dd ZeeeddZeeeddZeee	ddZede
ddZeedddZedfddZdd Zedd Zdd Zdd Zdd Zd d! Zd"d# Zd$d% ZdS )&MetricGroupManagerz
    Manages a dictionary of MetricGroups which can be pmFetch'ed
    inherits from MetricCache, which inherits from pmContext
    c                 C   rh   r(   _optionsr8   r    r    r!   
_R_options  rj   zMetricGroupManager._R_optionsc                 C   r{   r(   r   )r   optionsr    r    r!   
_W_options  r~   zMetricGroupManager._W_optionsc                 C   rh   r(   _default_deltar8   r    r    r!   _R_default_delta
  rj   z#MetricGroupManager._R_default_deltac                 C   r{   r(   r   )r   rd   r    r    r!   _W_default_delta  r~   z#MetricGroupManager._W_default_deltac                 C   rh   r(   _default_pauser8   r    r    r!   _R_default_pause  rj   z#MetricGroupManager._R_default_pausec                 C   r{   r(   r   r   pauser    r    r!   _W_default_pause  r~   z#MetricGroupManager._W_default_pausec                 C   r{   r(   )_printer)r   printerr    r    r!   
_W_printer  r~   zMetricGroupManager._W_printerc                 C   rh   r(   )_counterr8   r    r    r!   
_R_counter  rj   zMetricGroupManager._R_counterNr   c                 C   s@   t |  t| || d | _tdd| _d | _d | _d| _d S )NrI   r   )	r   r"   r   r   r   r   r   r   r  r   r    r    r!   r"   %  s   

zMetricGroupManager.__init__c                 C   r   r   r   r   r    r    r!   r   .  r   zMetricGroupManager.__setitem__c                 C   s$   |  ||}t|jd|_||_|S )z8 Helper interface, simple PCP monitor argument parsing. r   )fromOptionsr   rd   r   r   )clsr   argvr   r    r    r!   builder3  s   zMetricGroupManager.builderc                 C   s$   |du rdS t |jt |jd  S )z- convert timeval to epoch seconds as a float Nr   g    .A)r   tv_sectv_usec)r   tvr    r    r!   	_tv2float>  s   zMetricGroupManager._tv2floatc           	      C   s   | j du rdS d}|  D ]	}| | jrd}q| j  }|dur&|| dfS | j  du r/dS | j  }| j  }| j  }|du rE| j}| 	|}| 	|| 	| | }t
|d | |fS )a   Return the number of samples we are to take and the
            finish time, or 0,0 if --finish is not specified.
            This is based on command line options --samples but also
            must consider --start, --finish and --interval.  If none
            of these were presented, a zero return means "infinite".
            Also consider whether the utility needs rate-conversion,
            automatically increasing the sample count to accommodate
            when counters metrics are present.
        N)r   NrI   r   g      ?)r   r   r   pmGetOptionSamplespmGetOptionFinishOptargpmGetOptionOriginpmGetOptionFinishpmGetOptionIntervalr   r
  int)	r   extrar   samplesoriginfinishrd   periodwindowr    r    r!   _computeSamplesD  s(   







z"MetricGroupManager._computeSamplesc                 C   sp   | j dur| j S | jtkrtdd| _ | j S | jdur1| j }|dur*|| _ | j S | j| _ | j S | j| _ | j S )aV   Figure out how long to sleep between samples.
            This needs to take into account whether we were explicitly
            asked for a delay (independent of context type, --pause),
            whether this is an archive or live context, and the sampling
            --interval (including the default value, if none requested).
        Nr   )r   r/   r   r   r   r  r   r   r    r    r!   _computePauseTimec  s   

	

z$MetricGroupManager._computePauseTimec                 C   s   g }t t|  }t|D ]\}}t|ts|d}t |||< qzt| | W n* tyT   t|D ]\}}zt| | W q5 tyQ   |	||  Y q5w Y nw |sYdS |S )z
        Return a list of metrics that are missing from the default context.
        This is usually only applicable when replaying archives.
        Return None if all found, else a list of missing metric names.
        r   N)
r   r   r   r   r   r   r   r   r
   rS   )r   r   r   r   rW   r   r    r    r!   checkMissingMetricsx  s(   

z&MetricGroupManager.checkMissingMetricsc                 C   sJ   d}d}|   D ]}| |  }|du s| ||kr"|}| |}q|S )z/ Perform fetch operation on all of the groups. Nr   )r   r   r
  )r   	fetchtimermaxr   stampr    r    r!   fetch  s   
zMetricGroupManager.fetchc              
   C   s   |   \}}|  }z:|  }	 | j|  krdkrW dS  |dur/| || |kr/W dS | j|  |  |  }|  jd7  _q tyX } z|W  Y d}~S d}~w t	ya   Y dS w )av   Using options specification, loop fetching and reporting,
            pausing for the requested time interval between updates.
            Transparently handles archive/live mode differences.
            Note that this can be different to the sampling interval
            in archive mode, but is usually the same as the sampling
            interval in live mode.
        Tr   NrI   )
r  r  r  r  r
  r   r   sleepr   KeyboardInterrupt)r   r  r  timercurtimecoder    r    r!   run  s0   		zMetricGroupManager.run)r#   r$   r%   r&   r   r   r   r   r   r   r   r  r   r   default_deltadefault_pauser   counterr   r"   r   classmethodr  r
  r  r  r  r  r#  r    r    r    r!   r     s2    	

r   )r&   r   ctypesr   r   r   r   r   	pcp.pmapir   r   r	   r
   r   cpmapir   r   r   r   r   r   r   r   objectr   r'   r   r   r   r   r   r    r    r    r!   <module>   s    ( B{q