o
    i*                  
   @   sr  U d Z ddlZddlZddlZddlZddlZddlmZ ddlm	Z	m
Z
mZ ddlmZ ddlmZ ddlmZ ddlmZ dd	lmZ d
Zdegeg dZeed< ee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efdefd efd!efd"e fd#e!fd$e"fgZ$d!e#iZ%d%ee& fd&d'Z'd(d) Z(d*d+ Z)d,e&d-ed.ed/e*d%df
d0d1Z+d2d3 Z,dS )4z:Resizefs: cloud-config module which resizes the filesystem    N)Optional)	lifecyclesubputil)Cloud)Config)
MetaSchema)ALL_DISTROS)
PER_ALWAYSnoblockcc_resizefs)iddistros	frequencyactivate_by_schema_keysmetac                 C   s   t | stjd|  rddddd|  g}ndddd| g}tjd}tjtddgj	
dd	 
d
d  }||krM|d}||d d t|S )Nz%s/.snapshotsbtrfs
filesystemresizemaxz5.10z	--version
r   v   z	--enqueue)r   mount_is_read_writeospathisdirr   Versionfrom_strr   stdoutsplitstripindexinserttuple)mount_pointdevpthcmdbtrfs_with_queuesystem_btrfs_veridx r,   >/usr/lib/python3/dist-packages/cloudinit/config/cc_resizefs.py_resize_btrfs%   s.   

r.   c                 C   s   d|fS )N	resize2fsr,   r&   r'   r,   r,   r-   _resize_extI      r1   c                 C   s   d| fS )N
xfs_growfsr,   r0   r,   r,   r-   _resize_xfsM   r2   r4   c                 C   
   dd| fS )Ngrowfsz-yr,   r0   r,   r,   r-   _resize_ufsQ      
r7   c                 C   s   ddd| |fS )Nzpoolonlinez-er,   r0   r,   r,   r-   _resize_zfsU   s   r;   c                 C   r5   )Nhammer2r6   r,   r0   r,   r,   r-   _resize_hammer2Y   r8   r=   c                 C   s   ddd|fS )zSingle device resizebcachefsdevicer   r,   r0   r,   r,   r-   _resize_bcachefs]   s   r@   c              
   C   sb   d}d}zt  dd|g W dS  t jy0 } z|j|r*||jv r*W Y d }~dS |d }~ww )Nzgrowfs: requested sizez.is not larger than the current filesystem sizer6   z-NTF)r   ProcessExecutionErrorstderr
startswith)r&   r'   
skip_startskip_container,   r,   r-   _can_skip_resize_ufsb   s   rG   r   extxfsufszfsr<   r>   returnc              
   C   s   t  rtjntj}tjdstd d S ztdd| g\}}|r.t	d||  W d S W n tj
yI } z|d| | W Y d }~d S d }~ww d}|dD ]!}t||rr| |vrrd	|vrr| d
 }td| | |  S qQ|d| || d S )Nz/dev/zfsz"Cannot get zpool info, no /dev/zfsr9   statusz0zpool status returned error: [%s] for zpool [%s]z$Unable to get zpool status of %s: %sz.*(ONLINE).*r   stater   zfound zpool "%s" on disk %sz'No zpool found: [%s]: out: [%s] err: %s)r   is_containerLOGdebugwarningr   r   existsr   inforA   r!   research)r9   log_warnzpoolstatuserrrlinediskr,   r,   r-   get_device_info_from_zpool   s<   
r]   c                 C   s6   |   }t D ]\}}||r|||  S qdS )NF)lowerRESIZE_FS_PRECHECK_CMDSitemsrC   )fs_typeresize_whatr'   	fstype_lcifuncr,   r,   r-   can_skip_resize   s   
rf   c              
   C   sr  t  }| dkr(tj| s(|s(t t  } | du r"td dS t	d|  | dkr5t	d| | dS | 
drAt	d | S | 
d	s\tj| s\d	| d
 }t	d| | |} zt| }W n3 ty } z'|r{|jtjkr{t	d| | n|jtjkrtd| | n|W Y d}~dS d}~ww t|jst|js|rt	d| | dS td| | dS | S )a  Return updated devpath if the devpath is a writable block device.

    @param devpath: Requested path to the root device we want to resize.
    @param info: String representing information about the requested device.
    @param log: Logger to which logs will be added upon error.

    @returns devpath or updated devpath per kernel command line if the device
        path is a writable block device, returns None otherwise.
    z	/dev/rootNz!Unable to find device '/dev/root'z.Converted /dev/root to '%s' per kernel cmdlineoverlayrootz)Not attempting to resize devpath '%s': %szgpt/z#We have a gpt label - just go aheadz/dev//z:'%s' doesn't appear to be a valid device path. Trying '%s'z9Device '%s' did not exist in container. cannot resize: %sz,Device '%s' did not exist. cannot resize: %sz>device '%s' not a block device in container. cannot resize: %sz1device '%s' not a block device. cannot resize: %s)r   rO   r   r   rS   rootdev_from_cmdlineget_cmdlinerP   rR   rQ   rC   lstripstatOSErrorerrnoENOENTS_ISBLKst_modeS_ISCHR)devpathrT   	containerfulldevpathstatretexcr,   r,   r-   maybe_get_writable_device_path   sr   




rx   namecfgcloudargsc                 C   s  |r|d }nt |dd}t j|tgdstd|  d S d}t |t}|s0td| d S |\}}}	|dkrJ|dd }
t	|
}|sHd S |
}d	||	|f }td
| t
||}|s`d S d }t|||rqtd|| d S | }tD ]\}}||r|} nqw|std|| d S |||}td||d| |tkrt t| nt| d}|tkrd}td||| d S )Nr   resize_rootfsT)addonsz+Skipping module named %s, resizing disabledrh   z)Could not determine filesystem type of %srK   zdev=%s mnt_point=%s path=%szresize_info: %sz%Skip resize filesystem type %s for %sz.Not resizing unknown filesystem type %s for %szResizing %s (%s) using %s ResizedzResizing (via forking)z$%s root filesystem (type=%s, val=%s))r   get_cfg_option_strtranslate_boolNOBLOCKrP   rQ   get_mount_inforR   r!   r]   rx   rf   r^   RESIZE_FS_PREFIXES_CMDSrC   joinfork_cb	do_resize)ry   rz   r{   r|   resize_rootrb   resultr'   ra   r&   r9   rT   resizerrc   pfixroot_cmd
resize_cmdactionr,   r,   r-   handle   st   




r   c                 C   s2   zt  |  W d S  t jy   ttd|   w )Nz$Failed to resize filesystem (cmd=%s))r   rA   r   logexcrP   )r   r,   r,   r-   r   K  s   r   )-__doc__rn   loggingr   rU   rl   typingr   	cloudinitr   r   r   cloudinit.cloudr   cloudinit.configr   cloudinit.config.schemar   cloudinit.distrosr	   cloudinit.settingsr
   r   r   __annotations__	getLogger__name__rP   r.   r1   r4   r7   r;   r=   r@   rG   r   r_   strr]   rf   rx   listr   r   r,   r,   r,   r-   <module>   sT   
$
PP