܍~c4dZddlZddlZddlZddlZddlmZejeZ ej dddgZ dZ Gdd e Z dd ZddZddZdZddZdS)z9Common utility functions for interacting with subprocess.N)ENOEXEC SubpResultstdoutstderrc~g}g}g}|D]}t|tr6|d |dd}n|d|kr|d|nft|tr.|d|zs||n#|t||||r0t d||d||r7td |d||S) aEnsure user-provided commands start with base_command; warn otherwise. Each command is either a list or string. Perform the following: - If the command is a list, pop the first element if it is None - If the command is a list, insert base_command as the first element if not present. - When the command is a string not starting with 'base-command', warn. Allow flexibility to provide non-base-command environment/config setup if needed. @commands: List of commands. Each command element is a list or string. @return: List of 'fixed up' commands. @raise: TypeError on invalid config item type. rNz%s z Non-%s commands in %s config: %s zHInvalid {name} config. These commands are not a string or list: {errors})nameerrors) isinstancelistinsertstr startswithappendLOGwarningjoin TypeErrorformat) base_commandcommandswarningsr fixed_commandscommands 0/usr/lib/python3/dist-packages/cloudinit/subp.pyprepend_base_commandrsl"H FN ' ' gt $ $ qz!!!""+|++q,///  % % %%el&:;; )((( MM#g,, ' ' ' g&&&&  /   IIh        BBH&!$))F*;*;CICC   c:eZdZdZdZ ddZdZd dZdS) ProcessExecutionErrorzr%(description)s Command: %(cmd)s Exit code: %(exit_code)s Reason: %(reason)s Stdout: %(stdout)s Stderr: %(stderr)s-Nc N|s |j|_n||_|s|s|tkrd|_nd|_n||_t |t s |j|_n||_|s| |j|_n"||_n|||_|s| |j|_ n"||_ n|||_ |r||_ n |j|_ ||_ |j | |j| |j| |j| |j | |j| |j dz}t||dS)Nz(Exec format error. Missing #! in script?z'Unexpected error while running command.) descriptioncmd exit_coderrreason) empty_attrr$rr#r intr%r _indent_textrr&errno MESSAGE_TMPL_ensure_stringIOError__init__) selfrrr%r$r#r&r*messages rr.zProcessExecutionError.__init__Ns DHHDH + M'!1!1#M  #L  *D )S)) '!_DNN&DN 4~"o $ ++F33DK 4~"o $ ++F33DK  * DKK/DK #..t/?@@&&tx00,,T^<<))$+66))$+66))$+66 ' '   w'''''rcXt|tr|n|S)z1 if data is bytes object, decode r bytesdecode)r/texts rr,z$ProcessExecutionError._ensure_strings%!+4 7 7At{{}}}TArcd}d|z}t|tr(|}|}|||||zS)zY indent text on all but the first line, allowing for easy to read output r  )r r3encoderstripreplace)r/r5 indent_levelcrindents rr)z"ProcessExecutionError._indent_textse|# dE " " %B]]__F{{2&&r2;777r)NNNNNNN)r6)__name__ __module__ __qualname__r+r'r.r,r)rrr r Bsw J :(:(:(:(xBBB 8 8 8 8 8 8rr TFr;c N| td|dg}d} | r7| tj}|}|| t | dkrd| gt |z}| rKt|t rd|n|}| d ||s#t d ||||rd n|nt d |d}d}d}|rtj }tj }|rtj }tj}|ttj} | }n5tj }t|t"s|}t|t"r|}n7t|t&r|d }n d |D} tj||||||| }||\}}nA#t,$r4}| r | dt/|||jrdndrdnd|d}~wwxYw | r| n#| r| wwxYw|s|r|sd}|sd}rdfd }||}||}|j}||vr4| r| d |t/||||| r| d |t7||S)aRun a subprocess. :param args: command to run in a list. [cmd, arg1, arg2...] :param data: input to the command, made available on its stdin. :param rcs: a list of allowed return codes. If subprocess exits with a value not in this list, a ProcessExecutionError will be raised. By default, data is returned as a string. See 'decode' parameter. :param env: a dictionary for the command's environment. :param capture: boolean indicating if output should be captured. If True, then stderr and stdout will be returned. If False, they will not be redirected. :param combine_capture: boolean indicating if stderr should be redirected to stdout. When True, interleaved stderr and stdout will be returned as the first element of a tuple, the second will be empty string or bytes (per decode). if combine_capture is True, then output is captured independent of the value of capture. :param shell: boolean indicating if this should be run with a shell. :param logstring: the command will be logged to DEBUG. If it contains info that should not be logged, then logstring will be logged instead. :param decode: if False, no decoding will be done and returned stdout and stderr will be bytes. Other allowed values are 'strict', 'ignore', and 'replace'. These values are passed through to bytes().decode() as the 'errors' parameter. There is no support for decoding to other than utf-8. :param target: not supported, kwarg present only to make function signature similar to curtin's subp. :param update_env: update the enviornment for this command with this dictionary. this will not affect the current processes os.environ. :param status_cb: call this fuction with a single string argument before starting and after finishing. :param cwd: change the working directory to cwd before executing the command. :return if not capturing, return is (None, None) if capturing, stdout and stderr are returned. if decode: entries in tuple will be string if not decode: entries in tuple will be bytes Nz&target arg not supported by cloud-initr/chrootr8zBegin run command: {command} )rzFRunning command %s with allowed return codes %s (shell=%s, capture=%s)combinezFRunning hidden command to protect sensitive input/output logstring: %sutf-8cfg|].}t|tr|n|d/SrG)r r3r9).0xs r zsubp..sD   ABAu%% .ldecodeCs.dE**  ;;q&)) )rz%ERROR: End run command: exit({code}) )code)rrr%r$zEnd run command: exit({code}) rI) ValueErrorosenvironcopyupdate target_pathr r rrrdebug subprocessPIPESTDOUTopendevnullr3r9rPopen communicateOSErrorr r*close returncoder)argsrTrcsrNcapturecombine_capturerO logstringr4target update_env status_cbrP devnull_fprrMrr bytes_argsspouterrerVrcs ` rsubprxs!BABBB {cJ ;*Chhjj :6c!!&!DJJ.L$.tT$:$:D#((4... 299'9JJKKK    &   ( 5IIg       )    E F F!#" |"*%% $&& !;;==D $  D#   [[))   FJ         ^^D)) cc      L IJ K K K#' *33d *33d                         / C C  * * * * * * gcllgcll B }}  P I>EE2ENN O O O#sbd    E 3:::CCDDD c3  s*$3HI1 I"/III11J c|dvrd}net|tstd|ztj|}|dr |dd}|s|St|r1|ddkr%|dd}t|r |ddk%tj||S)N)NrDzUnexpected input for target: %sz//rr) r rrXrYpathabspathrlenr)rnr{s rr]r]Ws   $ $ :VCDDD((   T " " ABBZF   d))Q3ABBx d))Q3 7<< % %%rct|}tjj|vrt t||r|S|\dtjddtjD}|dkr|}n d|D}d|D}|D]I}tjj ||f}t t||r|cSJdS)Nc8g|]}|dS)")striprJps rrLzwhich..xs/   AGGCLL   rPATHrzrDc<g|]}|d|S)rD)rrs rrLzwhich..~s)<<.s& 1 1 1Qbgooa  1 1 1r) r]rYr{sepis_exerZgetsplitpathsepr)programsearchrnpathsr{ppaths rwhichrms  F w{g +fg.. / / N ~  "$*.."<"<"B"B2:"N"N    S==FF<<<<>% >RYubg%>%>>rc |r!tj|sdSg}g}|g}nMt|trt |g}n't|t r|}nt dttj|D]}tj ||}t|rr| | t||gzd]#t$r9}t|| |Yd}~d}~wwxYw|rH|rHt!dt#|dd |dt#|ddSdS) Nz%exe_prefix must be None, str, or listF)rkz Runparts: z failures (,z) in z attempted commands)rYr{isdirr rr rsortedlistdirrrrrxr rr^ RuntimeErrorr}) dirp skip_no_exist exe_prefixfailed attemptedprefixexe_nameexe_pathrvs rrunpartsrsRW]]400 FI J $ $Aj//" J % %A?@@@2:d++,,((7<<h// (   (   X & & & (Vxj(%88888( ( ( ( !  h'''''''' (  ( ) l6{{{{CHHV,,,,c)nnnn >       s"C88 D;/D66D;) NNNTFFFr;NNNNrS)NN)TN)__doc__ collectionsloggingrYr_r*r getLoggerr?r namedtuplerrr-r rxr]rrrrBrrrsI?? g!! #[ #L8X2F G G 000fZ8Z8Z8Z8Z8GZ8Z8Z8~       u u u u p&&&&,<???       r