o
    f"                     @   s|   d dl Z d dlZd dlZd dlmZ d dlZd dlmZmZ d dl	m
Z
 d dlmZmZ e eZG dd dejjjZdS )    N)StringIO)subputil)FreeBSDNetworking)
PER_ALWAYSPER_INSTANCEc                   @   s&  e Zd ZdZeZdZdZdZdZ	g dZ
ddgZdd	gZdd
gZddgZdZdZdZdZg dZed9ddZedddededefddZdd ZdefddZdd  Zd:d"d#Zd$d% Zd&d' Zd9d(d)Zd*d+ Z d!d,d-d.Z!e"d/ed0ed1ed2ed3ede#fd4d5Z$e"d6eddfd7d8Z%dS );DistrozY
    Distro subclass for FreeBSD.

    (N.B. DragonFlyBSD inherits from this class.)
    z/usr/local/libz/etc/login.confz/etc/login.conf.origz,/usr/local/etc/sudoers.d/90-cloud-init-users)pwgroupaddpkginstallremoveupdateupgradeTz	/usr/homez/var/dbzdhclient.leases.\w+)z^{username}::z^{username}:\*:z^{username}:\*LOCKED\*:Nc                 C   s8   t jd}|du rtd dS tjdd|gd|dS )z
        Tell rc to reload its configuration
        Note that this only works while we're still in the process of booting.
        May raise ProcessExecutionError
        RC_PIDNz0Unable to reload rc(8): no RC_PID in Environmentkillz-SIGALRMTcapturercs)osenvirongetLOGwarningr   )clsr   rc_pid r   ;/usr/lib/python3/dist-packages/cloudinit/distros/freebsd.pyreload_init7   s
   
zDistro.reload_init)r   actionservice
extra_argsc                G   sx   | j }|dg|dg|dg|dg|dg|dg|dg|dg|dg|dg|d	g|d
gd}|||  t| }tj|d|dS )a  
        Perform the requested action on a service. This handles FreeBSD's
        'service' case. The FreeBSD 'service' is closer in features to
        'systemctl' than SysV init's 'service', so we override it.
        May raise ProcessExecutionError
        stopstartenableenableddisableonestartonestoprestartstatus	onestatus)r#   r$   r%   r&   r'   r(   r)   r*   reloadz
try-reloadr+   r,   Tr   )init_cmdlistr   )r   r    r!   r   r"   r.   cmdscmdr   r   r   manage_serviceE   s    
zDistro.manage_servicec                 C   s   ddd|d|gS )Nr	   usermod-n-Gr   )selfmember_name
group_namer   r   r   _get_add_member_to_group_cmda   s   z#Distro._get_add_member_to_group_cmdreturnc                 K   s  t |rtd| dS ddd|g}ddd|g}dddd	d
ddd}dddd}| D ]1\}}||v rJ|rJt|ttfrJ||| t|g q-||v r^|r^|	||  |	||  q-d|v sgd|v rr|	d |	d n$|
d| j d| }	|	d|	  |	d |	d|	  |	d td| z	tj||d W n ty   t td|  w |
dd}
|
dur| j||
dd dS )z~
        Add a user to the system using standard tools

        Returns False if user already exists, otherwise True.
        z!User %s already exists, skipping.Fr	   useraddr4   z-d-cz-gr5   z-sz-Ez-u)homedirgecosprimary_groupgroupsshellinactiveuidz--no-user-groupz--systemz--no-log-init)no_user_groupsystemno_log_initno_create_homerE   z-d/nonexistentr=   /z-mzAdding user %s)	logstringzFailed to create user %spasswdNT)hashed)r   is_userr   infoitems
isinstancestrintextendappendr   home_dirr   	Exceptionlogexc
set_passwd)r6   namekwargspw_useradd_cmdlog_pw_useradd_cmdpw_useradd_optspw_useradd_flagskeyvalr=   
passwd_valr   r   r   add_userd   sV   




zDistro.add_userc                 C   :   zt  dd|ddg W d S  ty   ttd|  w )Nr	   r3   -pz01-Jan-1970z"Failed to set pw expiration for %sr   rU   r   rV   r   )r6   userr   r   r   expire_passwd      zDistro.expire_passwdFc                 C   sR   |rd}nd}zt j dd||dg|d| d W d S  ty(   ttd|  w )	Nz-Hz-hr	   r3   0zchpasswd for %s)datarI   zFailed to set password for %srd   )r6   re   rJ   rK   hash_optr   r   r   rW      s   zDistro.set_passwdc                 C   rb   )Nr	   r3   z-wnoz)Failed to lock password login for user %srd   r6   rX   r   r   r   lock_passwd   rg   zDistro.lock_passwdc                 C   s   t d| d S )NzRDragonfly BSD/FreeBSD password lock is not reversible, ignoring unlock for user %s)r   debugrl   r   r   r   unlock_passwd   s   zDistro.unlock_passwdc                 C   s   t  }t| j D ]}|tdd| | |d qt| j| j	 t
| j|  ztd| td| jg W d S  tjyp   ttd| zt| j	| j W Y d S  tyo   ttd| j Y Y d S w w )Nz	^default:zdefault:lang=%s:
zRunning cap_mkdb for %scap_mkdbzFailed to apply locale %szFailed to restore %s backup)r   r   load_text_filelogin_conf_fn
splitlineswriteresubcopylogin_conf_fn_bak
write_filegetvaluer   rn   r   ProcessExecutionErrorrV   IOError)r6   localeout_fnnewconfliner   r   r   apply_locale   s*   zDistro.apply_localec                 C   s   ddiS )zJReturn environment vars used in FreeBSD package_command
        operationsASSUME_ALWAYS_YESYESr   )r6   r   r   r   _get_pkg_cmd_environ   s   zDistro._get_pkg_cmd_environ)forcec                C   s$   | j jd| jdg|rtntd d S )Nzupdate-sourcesr   )freq)_runnerrunpackage_commandr   r   )r6   r   r   r   r   update_package_sources   s   

zDistro.update_package_sourcespath
lease_filepid_file	interfaceconfig_filec                 C   s$   | d|d|g|rd||g S |g S )Nz-lrc   r<   r   )r   r   r   r   r   r   r   r   build_dhclient_cmd   s
   zDistro.build_dhclient_cmddevicec                 C   s   t  dd| g d S )N
camcontroleject)r   )r   r   r   r   eject_media   s   zDistro.eject_media)N)F)&__name__
__module____qualname____doc__r   networking_clsusr_lib_execrs   ry   ci_sudoers_fngroup_add_cmd_prefixpkg_cmd_install_prefixpkg_cmd_remove_prefixpkg_cmd_update_prefixpkg_cmd_upgrade_prefixprefer_fqdnrT   dhclient_lease_directorydhclient_lease_file_regex#shadow_empty_locked_passwd_patternsclassmethodr   rP   r2   r9   boolra   rf   rW   rm   ro   r   r   r   staticmethodr/   r   r   r   r   r   r   r      sj    >

r   )loggingr   rv   ior   cloudinit.distros.bsd	cloudinitr   r   cloudinit.distros.networkingr   cloudinit.settingsr   r   	getLoggerr   r   distrosbsdBSDr   r   r   r   r   <module>   s   
