# SPDX-License-Identifier: Apache-2.0
# Copyright 2013-2019 The Meson development team

# This file contains the detection logic for miscellaneous external dependencies.
from __future__ import annotations

import functools
import re
import typing as T

from .. import mesonlib
from .. import mlog
from .base import DependencyException, DependencyMethods
from .base import BuiltinDependency, SystemDependency
from .cmake import CMakeDependency, CMakeDependencyFactory
from .configtool import ConfigToolDependency
from .detect import packages
from .factory import DependencyFactory, factory_methods
from .pkgconfig import PkgConfigDependency
from ..options import OptionKey

if T.TYPE_CHECKING:
    from ..environment import Environment
    from .factory import DependencyGenerator


@factory_methods({DependencyMethods.PKGCONFIG, DependencyMethods.CMAKE})
def netcdf_factory(env: 'Environment',
                   for_machine: 'mesonlib.MachineChoice',
                   kwargs: T.Dict[str, T.Any],
                   methods: T.List[DependencyMethods]) -> T.List['DependencyGenerator']:
    language = kwargs.get('language')
    if language is None:
        language = 'c'
    if language not in ('c', 'cpp', 'fortran'):
        raise DependencyException(f'Language {language} is not supported with NetCDF.')

    candidates: T.List['DependencyGenerator'] = []

    if DependencyMethods.PKGCONFIG in methods:
        if language == 'fortran':
            pkg = 'netcdf-fortran'
        else:
            pkg = 'netcdf'

        candidates.append(functools.partial(PkgConfigDependency, pkg, env, kwargs, language=language))

    if DependencyMethods.CMAKE in methods:
        candidates.append(functools.partial(CMakeDependency, 'NetCDF', env, kwargs, language=language))

    return candidates

packages['netcdf'] = netcdf_factory


class AtomicBuiltinDependency(BuiltinDependency):
    def __init__(self, name: str, env: Environment, kwargs: T.Dict[str, T.Any]):
        super().__init__(name, env, kwargs)
        self.feature_since = ('1.7.0', "consider checking for `atomic_flag_clear` with and without `find_library('atomic')`")

        if self.clib_compiler.has_function('atomic_flag_clear', '#include <stdatomic.h>', env)[0]:
            self.is_found = True


class AtomicSystemDependency(SystemDependency):
    def __init__(self, name: str, env: Environment, kwargs: T.Dict[str, T.Any]):
        super().__init__(name, env, kwargs)
        self.feature_since = ('1.7.0', "consider checking for `atomic_flag_clear` with and without `find_library('atomic')`")

        h = self.clib_compiler.has_header('stdatomic.h', '', env)
        self.link_args = self.clib_compiler.find_library('atomic', env, [], self.libtype)

        if h[0] and self.link_args:
            self.is_found = True


class DlBuiltinDependency(BuiltinDependency):
    def __init__(self, name: str, env: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, env, kwargs)
        self.feature_since = ('0.62.0', "consider checking for `dlopen` with and without `find_library('dl')`")

        if self.clib_compiler.has_function('dlopen', '#include <dlfcn.h>', env)[0]:
            self.is_found = True


class DlSystemDependency(SystemDependency):
    def __init__(self, name: str, env: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, env, kwargs)
        self.feature_since = ('0.62.0', "consider checking for `dlopen` with and without `find_library('dl')`")

        h = self.clib_compiler.has_header('dlfcn.h', '', env)
        self.link_args = self.clib_compiler.find_library('dl', env, [], self.libtype)

        if h[0] and self.link_args:
            self.is_found = True


class OpenMPDependency(SystemDependency):
    # Map date of specification release (which is the macro value) to a version.
    VERSIONS = {
        '202111': '5.2',
        '202011': '5.1',
        '201811': '5.0',
        '201611': '5.0-revision1',  # This is supported by ICC 19.x
        '201511': '4.5',
        '201307': '4.0',
        '201107': '3.1',
        '200805': '3.0',
        '200505': '2.5',
        '200203': '2.0',
        '199810': '1.0',
    }

    def __init__(self, environment: 'Environment', kwargs: T.Dict[str, T.Any]) -> None:
        language = kwargs.get('language')
        super().__init__('openmp', environment, kwargs, language=language)
        self.is_found = False
        if self.clib_compiler.get_id() == 'nagfor':
            # No macro defined for OpenMP, but OpenMP 3.1 is supported.
            self.version = '3.1'
            self.is_found = True
            self.compile_args = self.link_args = self.clib_compiler.openmp_flags(environment)
            return
        if self.clib_compiler.get_id() == 'pgi':
            # through at least PGI 19.4, there is no macro defined for OpenMP, but OpenMP 3.1 is supported.
            self.version = '3.1'
            self.is_found = True
            self.compile_args = self.link_args = self.clib_compiler.openmp_flags(environment)
            return

        # Set these now so they're available for the following compiler checks
        try:
            self.compile_args.extend(self.clib_compiler.openmp_flags(environment))
            self.link_args.extend(self.clib_compiler.openmp_link_flags(environment))
        except mesonlib.MesonException as e:
            mlog.warning('OpenMP support not available because:', str(e), fatal=False)
            return

        try:
            openmp_date = self.clib_compiler.get_define(
                '_OPENMP', '', self.env, [], [self], disable_cache=True)[0]
        except mesonlib.EnvironmentException as e:
            mlog.debug('OpenMP support not available in the compiler')
            mlog.debug(e)
            return

        try:
            self.version = self.VERSIONS[openmp_date]
        except KeyError:
            mlog.debug(f'Could not find an OpenMP version matching {openmp_date}')
            if openmp_date == '_OPENMP':
                mlog.debug('This can be caused by flags such as gcc\'s `-fdirectives-only`, which affect preprocessor behavior.')
            return

        # Flang has omp_lib.h
        header_names = ('omp.h', 'omp_lib.h')
        for name in header_names:
            if self.clib_compiler.has_header(name, '', self.env, dependencies=[self], disable_cache=True)[0]:
                self.is_found = True
                break
        else:
            mlog.warning('OpenMP found but omp.h missing.', fatal=False)

packages['openmp'] = OpenMPDependency


class ThreadDependency(SystemDependency):
    def __init__(self, name: str, environment: 'Environment', kwargs: T.Dict[str, T.Any]) -> None:
        super().__init__(name, environment, kwargs)
        self.is_found = True
        # Happens if you are using a language with threads
        # concept without C, such as plain Cuda.
        if not self.clib_compiler:
            self.compile_args = []
            self.link_args = []
        else:
            self.compile_args = self.clib_compiler.thread_flags(environment)
            self.link_args = self.clib_compiler.thread_link_flags(environment)


class BlocksDependency(SystemDependency):
    def __init__(self, environment: 'Environment', kwargs: T.Dict[str, T.Any]) -> None:
        super().__init__('blocks', environment, kwargs)
        self.name = 'blocks'
        self.is_found = False

        if self.env.machines[self.for_machine].is_darwin():
            self.compile_args = []
            self.link_args = []
        else:
            self.compile_args = ['-fblocks']
            self.link_args = ['-lBlocksRuntime']

            if not self.clib_compiler.has_header('Block.h', '', environment, disable_cache=True) or \
               not self.clib_compiler.find_library('BlocksRuntime', environment, []):
                mlog.log(mlog.red('ERROR:'), 'BlocksRuntime not found.')
                return

        source = '''
            int main(int argc, char **argv)
            {
                int (^callback)(void) = ^ int (void) { return 0; };
                return callback();
            }'''

        with self.clib_compiler.compile(source, extra_args=self.compile_args + self.link_args) as p:
            if p.returncode != 0:
                mlog.log(mlog.red('ERROR:'), 'Compiler does not support blocks extension.')
                return

            self.is_found = True

packages['blocks'] = BlocksDependency


class PcapDependencyConfigTool(ConfigToolDependency):

    tools = ['pcap-config']
    tool_name = 'pcap-config'

    # version 1.10.2 added error checking for invalid arguments
    # version 1.10.3 will hopefully add actual support for --version
    skip_version = '--help'

    def __init__(self, name: str, environment: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, environment, kwargs)
        if not self.is_found:
            return
        self.compile_args = self.get_config_value(['--cflags'], 'compile_args')
        self.link_args = self.get_config_value(['--libs'], 'link_args')
        if self.version is None:
            # older pcap-config versions don't support this
            self.version = self.get_pcap_lib_version()

    def get_pcap_lib_version(self) -> T.Optional[str]:
        # Since we seem to need to run a program to discover the pcap version,
        # we can't do that when cross-compiling
        # FIXME: this should be handled if we have an exe_wrapper
        if not self.env.machines.matches_build_machine(self.for_machine):
            return None

        v = self.clib_compiler.get_return_value('pcap_lib_version', 'string',
                                                '#include <pcap.h>', self.env, [], [self])
        v = re.sub(r'libpcap version ', '', str(v))
        v = re.sub(r' -- Apple version.*$', '', v)
        return v


class CupsDependencyConfigTool(ConfigToolDependency):

    tools = ['cups-config']
    tool_name = 'cups-config'

    def __init__(self, name: str, environment: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, environment, kwargs)
        if not self.is_found:
            return
        self.compile_args = self.get_config_value(['--cflags'], 'compile_args')
        self.link_args = self.get_config_value(['--ldflags', '--libs'], 'link_args')


class LibWmfDependencyConfigTool(ConfigToolDependency):

    tools = ['libwmf-config']
    tool_name = 'libwmf-config'

    def __init__(self, name: str, environment: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, environment, kwargs)
        if not self.is_found:
            return
        self.compile_args = self.get_config_value(['--cflags'], 'compile_args')
        self.link_args = self.get_config_value(['--libs'], 'link_args')


class LibGCryptDependencyConfigTool(ConfigToolDependency):

    tools = ['libgcrypt-config']
    tool_name = 'libgcrypt-config'

    def __init__(self, name: str, environment: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, environment, kwargs)
        if not self.is_found:
            return
        self.compile_args = self.get_config_value(['--cflags'], 'compile_args')
        self.link_args = self.get_config_value(['--libs'], 'link_args')
        self.version = self.get_config_value(['--version'], 'version')[0]


class GpgmeDependencyConfigTool(ConfigToolDependency):

    tools = ['gpgme-config']
    tool_name = 'gpg-config'

    def __init__(self, name: str, environment: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, environment, kwargs)
        if not self.is_found:
            return
        self.compile_args = self.get_config_value(['--cflags'], 'compile_args')
        self.link_args = self.get_config_value(['--libs'], 'link_args')
        self.version = self.get_config_value(['--version'], 'version')[0]


class ShadercDependency(SystemDependency):

    def __init__(self, environment: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__('shaderc', environment, kwargs)

        static_lib = 'shaderc_combined'
        shared_lib = 'shaderc_shared'

        libs = [shared_lib, static_lib]
        if self.static:
            libs.reverse()

        cc = self.get_compiler()

        for lib in libs:
            self.link_args = cc.find_library(lib, environment, [])
            if self.link_args is not None:
                self.is_found = True

                if self.static and lib != static_lib:
                    mlog.warning(f'Static library {static_lib!r} not found for dependency '
                                 f'{self.name!r}, may not be statically linked')

                break


class CursesConfigToolDependency(ConfigToolDependency):

    """Use the curses config tools."""

    tool = 'curses-config'
    # ncurses5.4-config is for macOS Catalina
    tools = ['ncursesw6-config', 'ncursesw5-config', 'ncurses6-config', 'ncurses5-config', 'ncurses5.4-config']

    def __init__(self, name: str, env: 'Environment', kwargs: T.Dict[str, T.Any], language: T.Optional[str] = None):
        exclude_paths = None
        # macOS mistakenly ships /usr/bin/ncurses5.4-config and a man page for
        # it, but none of the headers or libraries. Ignore /usr/bin because it
        # can only contain this broken configtool script.
        # Homebrew is /usr/local or /opt/homebrew.
        if env.machines.build and env.machines.build.system == 'darwin':
            exclude_paths = ['/usr/bin']
        super().__init__(name, env, kwargs, language, exclude_paths=exclude_paths)
        if not self.is_found:
            return
        self.compile_args = self.get_config_value(['--cflags'], 'compile_args')
        self.link_args = self.get_config_value(['--libs'], 'link_args')


class CursesSystemDependency(SystemDependency):

    """Curses dependency the hard way.

    This replaces hand rolled find_library() and has_header() calls. We
    provide this for portability reasons, there are a large number of curses
    implementations, and the differences between them can be very annoying.
    """

    def __init__(self, name: str, env: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, env, kwargs)

        candidates = [
            ('pdcurses', ['pdcurses/curses.h']),
            ('ncursesw',  ['ncursesw/ncurses.h', 'ncurses.h']),
            ('ncurses',  ['ncurses/ncurses.h', 'ncurses/curses.h', 'ncurses.h']),
            ('curses',  ['curses.h']),
        ]

        # Not sure how else to elegantly break out of both loops
        for lib, headers in candidates:
            l = self.clib_compiler.find_library(lib, env, [])
            if l:
                for header in headers:
                    h = self.clib_compiler.has_header(header, '', env)
                    if h[0]:
                        self.is_found = True
                        self.link_args = l
                        # Not sure how to find version for non-ncurses curses
                        # implementations. The one in illumos/OpenIndiana
                        # doesn't seem to have a version defined in the header.
                        if lib.startswith('ncurses'):
                            v, _ = self.clib_compiler.get_define('NCURSES_VERSION', f'#include <{header}>', env, [], [self])
                            self.version = v.strip('"')
                        if lib.startswith('pdcurses'):
                            v_major, _ = self.clib_compiler.get_define('PDC_VER_MAJOR', f'#include <{header}>', env, [], [self])
                            v_minor, _ = self.clib_compiler.get_define('PDC_VER_MINOR', f'#include <{header}>', env, [], [self])
                            self.version = f'{v_major}.{v_minor}'

                        # Check the version if possible, emit a warning if we can't
                        req = kwargs.get('version')
                        if req:
                            if self.version:
                                self.is_found, *_ = mesonlib.version_compare_many(self.version, req)
                            else:
                                mlog.warning('Cannot determine version of curses to compare against.')

                        if self.is_found:
                            mlog.debug('Curses library:', l)
                            mlog.debug('Curses header:', header)
                            break
            if self.is_found:
                break


class IconvBuiltinDependency(BuiltinDependency):
    def __init__(self, name: str, env: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, env, kwargs)
        self.feature_since = ('0.60.0', "consider checking for `iconv_open` with and without `find_library('iconv')`")
        code = '''#include <iconv.h>\n\nint main() {\n    iconv_open("","");\n}''' # [ignore encoding] this is C, not python, Mr. Lint

        if self.clib_compiler.links(code, env)[0]:
            self.is_found = True


class IconvSystemDependency(SystemDependency):
    def __init__(self, name: str, env: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, env, kwargs)
        self.feature_since = ('0.60.0', "consider checking for `iconv_open` with and without find_library('iconv')")

        h = self.clib_compiler.has_header('iconv.h', '', env)
        self.link_args = self.clib_compiler.find_library('iconv', env, [], self.libtype)

        if h[0] and self.link_args:
            self.is_found = True


class IntlBuiltinDependency(BuiltinDependency):
    def __init__(self, name: str, env: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, env, kwargs)
        self.feature_since = ('0.59.0', "consider checking for `ngettext` with and without `find_library('intl')`")
        code = '''#include <libintl.h>\n\nint main() {\n    gettext("Hello world");\n}'''

        if self.clib_compiler.links(code, env)[0]:
            self.is_found = True


class IntlSystemDependency(SystemDependency):
    def __init__(self, name: str, env: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, env, kwargs)
        self.feature_since = ('0.59.0', "consider checking for `ngettext` with and without `find_library('intl')`")

        h = self.clib_compiler.has_header('libintl.h', '', env)
        self.link_args = self.clib_compiler.find_library('intl', env, [], self.libtype)

        if h[0] and self.link_args:
            self.is_found = True

            if self.static:
                if not self._add_sub_dependency(iconv_factory(env, self.for_machine, {'static': True})):
                    self.is_found = False


class OpensslSystemDependency(SystemDependency):
    def __init__(self, name: str, env: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__(name, env, kwargs)

        dependency_kwargs = {
            'method': 'system',
            'static': self.static,
        }
        if not self.clib_compiler.has_header('openssl/ssl.h', '', env)[0]:
            return

        # openssl >= 3 only
        self.version = self.clib_compiler.get_define('OPENSSL_VERSION_STR', '#include <openssl/opensslv.h>', env, [], [self])[0]
        # openssl < 3 only
        if not self.version:
            version_hex = self.clib_compiler.get_define('OPENSSL_VERSION_NUMBER', '#include <openssl/opensslv.h>', env, [], [self])[0]
            if not version_hex:
                return
            version_hex = version_hex.rstrip('L')
            version_ints = [((int(version_hex.rstrip('L'), 16) >> 4 + i) & 0xFF) for i in (24, 16, 8, 0)]
            # since this is openssl, the format is 1.2.3a in four parts
            self.version = '.'.join(str(i) for i in version_ints[:3]) + chr(ord('a') + version_ints[3] - 1)

        if name == 'openssl':
            if self._add_sub_dependency(libssl_factory(env, self.for_machine, dependency_kwargs)) and \
                    self._add_sub_dependency(libcrypto_factory(env, self.for_machine, dependency_kwargs)):
                self.is_found = True
            return
        else:
            self.link_args = self.clib_compiler.find_library(name.lstrip('lib'), env, [], self.libtype)
            if not self.link_args:
                return

        if not self.static:
            self.is_found = True
        else:
            if name == 'libssl':
                if self._add_sub_dependency(libcrypto_factory(env, self.for_machine, dependency_kwargs)):
                    self.is_found = True
            elif name == 'libcrypto':
                use_threads = self.clib_compiler.has_header_symbol('openssl/opensslconf.h', 'OPENSSL_THREADS', '', env, dependencies=[self])[0]
                if not use_threads or self._add_sub_dependency(threads_factory(env, self.for_machine, {})):
                    self.is_found = True
                # only relevant on platforms where it is distributed with the libc, in which case it always succeeds
                sublib = self.clib_compiler.find_library('dl', env, [], self.libtype)
                if sublib:
                    self.link_args.extend(sublib)


class ObjFWDependency(ConfigToolDependency):

    tools = ['objfw-config']
    tool_name = 'objfw-config'

    def __init__(self, environment: 'Environment', kwargs: T.Dict[str, T.Any]):
        super().__init__('objfw', environment, kwargs)
        self.feature_since = ('1.5.0', '')
        if not self.is_found:
            return

        # TODO: Expose --reexport
        # TODO: Expose --framework-libs
        extra_flags = []

        for module in mesonlib.stringlistify(mesonlib.extract_as_list(kwargs, 'modules')):
            extra_flags.append('--package')
            extra_flags.append(module)

        # TODO: Once Meson supports adding flags per language, only add --objcflags to ObjC
        self.compile_args = self.get_config_value(['--cppflags', '--cflags', '--objcflags'] + extra_flags, 'compile_args')
        self.link_args = self.get_config_value(['--ldflags', '--libs'] + extra_flags, 'link_args')


@factory_methods({DependencyMethods.PKGCONFIG, DependencyMethods.CONFIG_TOOL, DependencyMethods.SYSTEM})
def curses_factory(env: 'Environment',
                   for_machine: 'mesonlib.MachineChoice',
                   kwargs: T.Dict[str, T.Any],
                   methods: T.List[DependencyMethods]) -> T.List['DependencyGenerator']:
    candidates: T.List['DependencyGenerator'] = []

    if DependencyMethods.PKGCONFIG in methods:
        pkgconfig_files = ['pdcurses', 'ncursesw', 'ncurses', 'curses']
        for pkg in pkgconfig_files:
            candidates.append(functools.partial(PkgConfigDependency, pkg, env, kwargs))

    # There are path handling problems with these methods on msys, and they
    # don't apply to windows otherwise (cygwin is handled separately from
    # windows)
    if not env.machines[for_machine].is_windows():
        if DependencyMethods.CONFIG_TOOL in methods:
            candidates.append(functools.partial(CursesConfigToolDependency, 'curses', env, kwargs))

        if DependencyMethods.SYSTEM in methods:
            candidates.append(functools.partial(CursesSystemDependency, 'curses', env, kwargs))

    return candidates
packages['curses'] = curses_factory


@factory_methods({DependencyMethods.PKGCONFIG, DependencyMethods.SYSTEM})
def shaderc_factory(env: 'Environment',
                    for_machine: 'mesonlib.MachineChoice',
                    kwargs: T.Dict[str, T.Any],
                    methods: T.List[DependencyMethods]) -> T.List['DependencyGenerator']:
    """Custom DependencyFactory for ShaderC.

    ShaderC's odd you get three different libraries from the same build
    thing are just easier to represent as a separate function than
    twisting DependencyFactory even more.
    """
    candidates: T.List['DependencyGenerator'] = []

    if DependencyMethods.PKGCONFIG in methods:
        # ShaderC packages their shared and static libs together
        # and provides different pkg-config files for each one. We
        # smooth over this difference by handling the static
        # keyword before handing off to the pkg-config handler.
        shared_libs = ['shaderc']
        static_libs = ['shaderc_combined', 'shaderc_static']

        if kwargs.get('static', env.coredata.get_option(OptionKey('prefer_static'))):
            c = [functools.partial(PkgConfigDependency, name, env, kwargs)
                 for name in static_libs + shared_libs]
        else:
            c = [functools.partial(PkgConfigDependency, name, env, kwargs)
                 for name in shared_libs + static_libs]
        candidates.extend(c)

    if DependencyMethods.SYSTEM in methods:
        candidates.append(functools.partial(ShadercDependency, env, kwargs))

    return candidates
packages['shaderc'] = shaderc_factory


packages['atomic'] = atomic_factory = DependencyFactory(
    'atomic',
    [DependencyMethods.SYSTEM, DependencyMethods.BUILTIN],
    system_class=AtomicSystemDependency,
    builtin_class=AtomicBuiltinDependency,
)

packages['cups'] = cups_factory = DependencyFactory(
    'cups',
    [DependencyMethods.PKGCONFIG, DependencyMethods.CONFIG_TOOL, DependencyMethods.EXTRAFRAMEWORK, DependencyMethods.CMAKE],
    configtool_class=CupsDependencyConfigTool,
    cmake_name='Cups',
)

packages['dl'] = dl_factory = DependencyFactory(
    'dl',
    [DependencyMethods.BUILTIN, DependencyMethods.SYSTEM],
    builtin_class=DlBuiltinDependency,
    system_class=DlSystemDependency,
)

packages['gpgme'] = gpgme_factory = DependencyFactory(
    'gpgme',
    [DependencyMethods.PKGCONFIG, DependencyMethods.CONFIG_TOOL],
    configtool_class=GpgmeDependencyConfigTool,
)

packages['libgcrypt'] = libgcrypt_factory = DependencyFactory(
    'libgcrypt',
    [DependencyMethods.PKGCONFIG, DependencyMethods.CONFIG_TOOL],
    configtool_class=LibGCryptDependencyConfigTool,
)

packages['libwmf'] = libwmf_factory = DependencyFactory(
    'libwmf',
    [DependencyMethods.PKGCONFIG, DependencyMethods.CONFIG_TOOL],
    configtool_class=LibWmfDependencyConfigTool,
)

packages['pcap'] = pcap_factory = DependencyFactory(
    'pcap',
    [DependencyMethods.PKGCONFIG, DependencyMethods.CONFIG_TOOL],
    configtool_class=PcapDependencyConfigTool,
    pkgconfig_name='libpcap',
)

packages['threads'] = threads_factory = DependencyFactory(
    'threads',
    [DependencyMethods.SYSTEM, DependencyMethods.CMAKE],
    cmake_name='Threads',
    system_class=ThreadDependency,
)

packages['iconv'] = iconv_factory = DependencyFactory(
    'iconv',
    [DependencyMethods.BUILTIN, DependencyMethods.SYSTEM],
    builtin_class=IconvBuiltinDependency,
    system_class=IconvSystemDependency,
)

packages['intl'] = intl_factory = DependencyFactory(
    'intl',
    [DependencyMethods.BUILTIN, DependencyMethods.SYSTEM],
    builtin_class=IntlBuiltinDependency,
    system_class=IntlSystemDependency,
)

packages['openssl'] = openssl_factory = DependencyFactory(
    'openssl',
    [DependencyMethods.PKGCONFIG, DependencyMethods.SYSTEM, DependencyMethods.CMAKE],
    system_class=OpensslSystemDependency,
    cmake_class=CMakeDependencyFactory('OpenSSL', modules=['OpenSSL::Crypto', 'OpenSSL::SSL']),
)

packages['libcrypto'] = libcrypto_factory = DependencyFactory(
    'libcrypto',
    [DependencyMethods.PKGCONFIG, DependencyMethods.SYSTEM, DependencyMethods.CMAKE],
    system_class=OpensslSystemDependency,
    cmake_class=CMakeDependencyFactory('OpenSSL', modules=['OpenSSL::Crypto']),
)

packages['libssl'] = libssl_factory = DependencyFactory(
    'libssl',
    [DependencyMethods.PKGCONFIG, DependencyMethods.SYSTEM, DependencyMethods.CMAKE],
    system_class=OpensslSystemDependency,
    cmake_class=CMakeDependencyFactory('OpenSSL', modules=['OpenSSL::SSL']),
)

packages['objfw'] = ObjFWDependency
