a 'DgLT@sdZddlZddlZddlZddlZddlZddlmZmZm Z m Z m Z m Z ddl mZmZmZmZmZddlmZddlmZmZmZmZddlmZeeZdd iZd Z d Z!d Z"e!d Z#e"d Z$ddiZ%dZ&Gddde Z'Gdddej(Z)eddddZ*Gdddej+Z,Gddde,Z-e.dddZ/e e.dd d!Z0e1dd"d#Z2e.e3d$d%d&Z4e.e ee.e.fd$d'd(Z5e.e.d$d)d*Z6d e,j7e,j8e#gd+e1e e.e e'd,d-d.Z9e,ej:ffe-ej:ej;ffgZe?e@e9e$e#gd3e2d4dS)5a3Datasource for Oracle (OCI/Oracle Cloud Infrastructure) Notes: * This datasource does not support OCI Classic. OCI Classic provides an EC2 lookalike metadata service. * The UUID provided in DMI data is not the same as the meta-data provided instance-id, but has an equivalent lifespan. * We do need to support upgrade from an instance that cloud-init identified as OpenStack. * Bare metal instances use iSCSI root, virtual machine instances do not. * Both bare metal and virtual machine instances provide a chassis-asset-tag of OracleCloud.com. N)AnyDictList NamedTupleOptionalTuple) atomic_helperdminetsourcesutil) NetworkConfig)cmdline ephemeralget_interfaces_by_macis_netfail_master) wait_for_urlconfigure_secondary_nicsFzOracleCloud.comz&http://169.254.169.254/opc/v{version}/z+http://[fd00:c1::a9fe:a9fe]/opc/v{version}/z{path}/Z Authorizationz Bearer Oraclei(#c@sBeZdZUeed<eeefed<eeeefed<eed<dS)ReadOpcMetadataResponseversion instance_data vnics_data imds_url_usedN) __name__ __module__ __qualname__int__annotations__rstrrrrrF/usr/lib/python3.9/site-packages/cloudinit/sources/DataSourceOracle.pyr4s rc@seZdZdZedddZdS)KlibcOracleNetworkConfigSourcezOverride super class to lower the applicability conditions. If any `/run/net-*.cfg` files exist, then it is applicable. Even if `/run/initramfs/open-iscsi.interface` does not exist. returncCs t|jS)zOverride is_applicable)bool_filesselfrrr is_applicableBsz,KlibcOracleNetworkConfigSource.is_applicableN)rrr__doc__r$r(rrrr r!;sr!)network_configr#cCsd|vr dS|ddvr,td|ddSt}|ddkrdd|dDD]@}|d d krPd |vrP|d }||}|sqPqPt|rP|d =qPn||dd kr|d iD]\\}}d|vr|did}|r||}|sqqt|r|dd=|d=||dd<qdS)aP Search network config physical interfaces to see if any of them are a netfailover master. If found, we prevent matching by MAC as the other failover devices have the same MAC but need to be ignored. Note: we rely on cloudinit.net changes which prevent netfailover devices from being present in the provided network config. For more details about netfailover devices, refer to cloudinit.net module. :param network_config A v1 or v2 network config dict with the primary NIC, and possibly secondary nic configured. This dict will be mutated. rN)z+Ignoring unknown network config version: %sr+cSsg|]}d|vr|qS)typer).0crrr cz,_ensure_netfailover_safe..configr-physical mac_addressr, ethernetsmatch macaddresszset-namename)LOGdebugrgetritems)r*Z mac_to_nameZcfgZmacZcur_name_Zmacaddrrrr _ensure_netfailover_safeGs>       r>cseZdZUdZdZejjejjejj ejj fZ e ejdfe d<dZdZdZfdd Zedd fd d Zed ddZeed ddZddZed ddZddZed ddZed ddZeddZd"edd d!Z Z!S)#DataSourceOracleZOracleN.network_config_sourcesTcsttt|j|g|Ri|d|_tt|d|jgitg|_ t |_ gdd|_ | }|j|_|j|_dS)NZ datasourcer+r2r)superr?__init__ _vnics_datar Z mergemanydictZget_cfg_by_pathdsnameBUILTIN_DS_CONFIGds_cfgr!_network_config_source_network_configZget_url_paramsZmax_wait_seconds url_max_waitZtimeout_seconds url_timeout)r'sys_cfgargskwargsZ url_params __class__rr rEs zDataSourceOracle.__init__)ci_pkl_versionr#csTt|t|ds"t|ddt|ds:t|dtt|dsPgdd|_dS)NrFrJrKr+rC)rD _unpicklehasattrsetattrr!rK)r'rSrQrr rTs     zDataSourceOracle._unpickler"cCst|jdgS)Nr2)r$rKr;r&rrr _has_network_configsz$DataSourceOracle._has_network_configcCstS)z@Check platform environment to report if this datasource may run.)_is_platform_viablerrrr ds_detectszDataSourceOracle.ds_detectc Csht|_tjdddtddtjddditjdddtddtjdddif}|jrvt}t j |j |dd|d}nt }| }|jd td }|,t|p||j|jttgd }Wdn1s0Y|sd St|jd |_|j}|_|j|_|d |dd|d|dd|_d|vrd|dd}|rPt||_|dd|jd<dS)Nr,instancerpath)urlZheadersr]r+T)distroZ interfaceZipv6Zipv4connectivity_urls_datarfetch_vnics_datamax_waittimeoutmetadata_patternsFr]Z ociAdNameidrhostnameZ displayName)zavailability-zonez instance-idz launch-indexzlocal-hostnamer8metadata user_dataZssh_authorized_keys public_keys) _read_system_uuid system_uuidIPV4_METADATA_PATTERNformat V2_HEADERSIPV6_METADATA_PATTERNperform_dhcp_setupr Zfind_fallback_nicrZEphemeralIPNetworkr^r nullcontext_is_iscsi_rootrIr;rHread_opc_metadatarLrM _get_versioned_metadata_base_urlrmetadata_addressrZ_crawled_metadatarrFrhbase64Z b64decodeZ userdata_raw) r'r_Znic_nameZnetwork_contextZfetch_primary_nicZfetch_secondary_nicsZfetched_metadatadatarirrr _get_datas $     zDataSourceOracle._get_datacCs t|jS)zquickly check (local only) if self.instance_id is still valid On Oracle, the dmi-provided system uuid differs from the instance-id but has the same life-span.)r Zinstance_id_matches_system_uuidrl)r'rNrrr check_instance_id sz"DataSourceOracle.check_instance_idcCst|jdS)Nrj)r Znormalize_pubkey_datarhr;r&rrr get_public_ssh_keyssz$DataSourceOracle.get_public_ssh_keyscCs |jS)z)Return whether we are on a iscsi machine.)rJr(r&rrr rsszDataSourceOracle._is_iscsi_rootcCs |jSN)rJZ render_configr&rrr _get_iscsi_configsz"DataSourceOracle._get_iscsi_configcCs|r|jSd}|r$||_|s:tdd}|jdtd}|sT|rz| |Wnt yt tdYn0t |j|jS)zNetwork config is read from initramfs provided files Priority for primary network_config selection: - iscsi - imds If none is present, then we fall back to fallback configuration. FzLCould not obtain network configuration from initramfs. Falling back to IMDS.Trz+Failed to parse IMDS network configuration!)rWrKrsr}r9warningrIr;rH!_add_network_config_from_opc_imds Exceptionr Zlogexcr>)r' set_primaryZ set_secondaryrrr r*s0     zDataSourceOracle.network_configF)rc CsV|jdurtddS|s8d|jdvr8tddSt}|rH|jn |jdd}t|D]\}}|or|dk}|d}|dd o|d d  }||vrtd |q^||} |rt|d d} nt|d } |j ddkr|r|rddig} n ddig} n`g} |d rB| d|d d| j d|d rr| d|d dd| j d| d|t | d} |j d | q^|j ddkr^t d|id} | |j d| <|o|| d<|o| | d<|sBg| d<|d r| d |d d| j |d rB| d |d dd| j | |j d| <q^dS)aGenerate primary and/or secondary NIC config from IMDS and merge it. It will mutate the network config to include the secondary VNICs. :param set_primary: If True set primary interface. :raises: Exceptions are not handled within this function. Likely exceptions are KeyError/IndexError (if the IMDS returns valid JSON with unexpected contents). Nz#NIC data is UNSET but should not beZnicIndexrz\VNIC metadata indicates this is a bare metal machine; skipping secondary VNIC configuration.r+ZmacAddrZipv6SubnetCidrBlockFZ privateIpz)Interface with MAC %s not found; skippingZ ipv6AddressesZsubnetCidrBlockrr-Zdhcp6ZdhcpZstatic/)r-addressr3)r8r-r4mtusubnetsr2r,r7)rr6r5Zdhcp4 addresses) rFr9r~r enumeratelowerr; ipaddress ip_networkrKappend prefixlenMTU) r'rZinterfaces_by_macrindexZ vnic_dictZ is_primaryr4Z is_ipv6_onlyr8networkrZinterface_configrrr rHs              z2DataSourceOracle._add_network_config_from_opc_imds)F)"rrrrGrlr ZNetworkConfigSourceZCMD_LINEZ SYSTEM_CFGZDSZ INITRAMFSr@rrrqrLrMrErrTr$rW staticmethodrYryrzr{rsdictr}propertyr*r __classcell__rrrQr r?{s.   V -r?c@seZdZdZdS)DataSourceOracleNetFN)rrrrqrrrr rsrrvcCs|sdS|tddS)NFZopcr) startswithIPV4_METADATA_ROOTsplitrrrr _is_ipv4_metadata_urlsrr"cCstd}|durdS|S)Nz system-uuid)r read_dmi_datar)Zsys_uuidrrr rks rkcCstd}|tkS)Nzchassis-asset-tag)r rCHASSIS_ASSET_TAG)Z asset_tagrrr rXs rX)r]r#cCsd|vr dSdS)Nz/opc/v2/r,r+rrerrr _url_versionsrcCst|dkrtSdS)Nr,)rrorerrr _headers_cbsrcCsL|s|Sd|vr"|dddSd|vr<|dddStd|dS)zQ Remove everything following the version number in the metadata address. Zv2rzv2/Zv1zv1/zInvalid metadata address: N)r ValueErrorrerrr rusrur`)rardr#c sfdddD}td|t}t|||tddd\}}|sXtdd |d Std |t | d }t |} d } |rt| d dg|t||tddd\} } | rt | d } td| n tdt | || |S)a Fetch metadata from the /opc/ routes from the IMDS. Returns: Optional[ReadOpcMetadataResponse]: If fetching metadata fails, None. If fetching metadata succeeds, a namedtuple containing: - The metadata version as an integer - The JSON-decoded value of the instance data from the IMDS - The JSON-decoded value of the vnics data from the IMDS if `fetch_vnics_data` is True, else None. Alternatively, None if fetching metadata failed - The url that was used to fetch the metadata. This allows for later determining if v1 or v2 endppoint was used and whether the IMDS was reached via IPv4 or IPv6. cs$g|]}D]}|j|ddq qS)rZr[)rn)r.rZmetadata_patternrdrr r0sz%read_opc_metadata..)r,r+z*Attempting to fetch IMDS metadata from: %sg?T)urlsrbrcZ headers_cbZ sleep_timeZconnect_synchronouslyz-Failed to fetch IMDS metadata from any of: %sz, Nz7Successfully fetched instance metadata from IMDS at: %szutf-8rZZvnicsz4Successfully fetched vnics metadata from IMDS at: %sz+Failed to fetch IMDS network configuration!)r9r:time monotonicrrr~joinjsonloadsdecoderreplacer) rarbrcrdrZ start_timeZurl_that_workedZinstance_responserZmetadata_versionrZ vnics_urlZvnics_responserrr rts`      rtcCs t|tSr|)r Zlist_from_depends datasources)Zdependsrrr get_datasource_listGsr__main__z Query Oracle Cloud metadata and emit a JSON object with two keys: `read_opc_metadata` and `_is_platform_viable`. The values of each are the return values of the corresponding functions defined in DataSourceOracle.py.r)rtrX)Ar)rwrrZloggingrtypingrrrrrrZ cloudinitrr r r r Zcloudinit.distros.networkingr Z cloudinit.netrrrrZcloudinit.url_helperrZ getLoggerrr9rHrrZIPV6_METADATA_ROOTrmrprorrZKlibcNetworkConfigSourcer!r>Z DataSourcer?rrrrkr$rXrrrrurLrMrtZDEP_FILESYSTEMZ DEP_NETWORKrr descriptionprintZ json_dumpsrrrr sz     4C U