// © 2016 and later: Unicode, Inc. and others.
// License & terms of use: http://www.unicode.org/copyright.html
/*
*******************************************************************************
*   Copyright (C) 1996-2016, International Business Machines
*   Corporation and others.  All Rights Reserved.
*******************************************************************************
*   file name:  ucol_res.cpp
*   encoding:   UTF-8
*   tab size:   8 (not used)
*   indentation:4
*
* Description:
* This file contains dependencies that the collation run-time doesn't normally
* need. This mainly contains resource bundle usage and collation meta information
*
* Modification history
* Date        Name      Comments
* 1996-1999   various members of ICU team maintained C API for collation framework
* 02/16/2001  synwee    Added internal method getPrevSpecialCE
* 03/01/2001  synwee    Added maxexpansion functionality.
* 03/16/2001  weiv      Collation framework is rewritten in C and made UCA compliant
* 12/08/2004  grhoten   Split part of ucol.cpp into ucol_res.cpp
* 2012-2014   markus    Rewritten in C++ again.
*/

#include "unicode/utypes.h"

#if !UCONFIG_NO_COLLATION

#include "unicode/coll.h"
#include "unicode/localpointer.h"
#include "unicode/locid.h"
#include "unicode/tblcoll.h"
#include "unicode/ucol.h"
#include "unicode/uloc.h"
#include "unicode/unistr.h"
#include "unicode/ures.h"
#include "charstr.h"
#include "cmemory.h"
#include "cstring.h"
#include "collationdatareader.h"
#include "collationroot.h"
#include "collationtailoring.h"
#include "resource.h"
#include "putilimp.h"
#include "uassert.h"
#include "ucln_in.h"
#include "ucol_imp.h"
#include "uenumimp.h"
#include "ulist.h"
#include "umutex.h"
#include "unifiedcache.h"
#include "uresimp.h"
#include "ustrenum.h"
#include "utracimp.h"

U_NAMESPACE_BEGIN

namespace {

static const UChar *rootRules = NULL;
static int32_t rootRulesLength = 0;
static UResourceBundle *rootBundle = NULL;
static UInitOnce gInitOnceUcolRes = U_INITONCE_INITIALIZER;

}  // namespace

U_CDECL_BEGIN

static UBool U_CALLCONV
ucol_res_cleanup() {
    rootRules = NULL;
    rootRulesLength = 0;
    ures_close(rootBundle);
    rootBundle = NULL;
    gInitOnceUcolRes.reset();
    return TRUE;
}

void U_CALLCONV
CollationLoader::loadRootRules(UErrorCode &errorCode) {
    if(U_FAILURE(errorCode)) { return; }
    rootBundle = ures_open(U_ICUDATA_COLL, kRootLocaleName, &errorCode);
    if(U_FAILURE(errorCode)) { return; }
    rootRules = ures_getStringByKey(rootBundle, "UCARules", &rootRulesLength, &errorCode);
    if(U_FAILURE(errorCode)) {
        ures_close(rootBundle);
        rootBundle = NULL;
        return;
    }
    ucln_i18n_registerCleanup(UCLN_I18N_UCOL_RES, ucol_res_cleanup);
}

U_CDECL_END

void
CollationLoader::appendRootRules(UnicodeString &s) {
    UErrorCode errorCode = U_ZERO_ERROR;
    umtx_initOnce(gInitOnceUcolRes, CollationLoader::loadRootRules, errorCode);
    if(U_SUCCESS(errorCode)) {
        s.append(rootRules, rootRulesLength);
    }
}

void
CollationLoader::loadRules(const char *localeID, const char *collationType,
                           UnicodeString &rules, UErrorCode &errorCode) {
    if(U_FAILURE(errorCode)) { return; }
    U_ASSERT(collationType != NULL && *collationType != 0);
    // Copy the type for lowercasing.
    char type[16];
    int32_t typeLength = static_cast<int32_t>(uprv_strlen(collationType));
    if(typeLength >= UPRV_LENGTHOF(type)) {
        errorCode = U_ILLEGAL_ARGUMENT_ERROR;
        return;
    }
    uprv_memcpy(type, collationType, typeLength + 1);
    T_CString_toLowerCase(type);

    LocalUResourceBundlePointer bundle(ures_open(U_ICUDATA_COLL, localeID, &errorCode));
    LocalUResourceBundlePointer collations(
            ures_getByKey(bundle.getAlias(), "collations", NULL, &errorCode));
    LocalUResourceBundlePointer data(
            ures_getByKeyWithFallback(collations.getAlias(), type, NULL, &errorCode));
    int32_t length;
    const UChar *s =  ures_getStringByKey(data.getAlias(), "Sequence", &length, &errorCode);
    if(U_FAILURE(errorCode)) { return; }

    // No string pointer aliasing so that we need not hold onto the resource bundle.
    rules.setTo(s, length);
    if(rules.isBogus()) {
        errorCode = U_MEMORY_ALLOCATION_ERROR;
    }
}

template<> U_I18N_API
const CollationCacheEntry *
LocaleCacheKey<CollationCacheEntry>::createObject(const void *creationContext,
                                                  UErrorCode &errorCode) const {
    CollationLoader *loader =
            reinterpret_cast<CollationLoader *>(
                    const_cast<void *>(creationContext));
    return loader->createCacheEntry(errorCode);
}

const CollationCacheEntry *
CollationLoader::loadTailoring(const Locale &locale, UErrorCode &errorCode) {
    const CollationCacheEntry *rootEntry = CollationRoot::getRootCacheEntry(errorCode);
    if(U_FAILURE(errorCode)) { return NULL; }
    const char *name = locale.getName();
    if(*name == 0 || uprv_strcmp(name, "root") == 0) {

        // Have to add a ref.
        rootEntry->addRef();
        return rootEntry;
    }

    // Clear warning codes before loading where they get cached.
    errorCode = U_ZERO_ERROR;
    CollationLoader loader(rootEntry, locale, errorCode);

    // getCacheEntry adds a ref for us.
    return loader.getCacheEntry(errorCode);
}

CollationLoader::CollationLoader(const CollationCacheEntry *re, const Locale &requested,
                                 UErrorCode &errorCode)
        : cache(UnifiedCache::getInstance(errorCode)), rootEntry(re),
          validLocale(re->validLocale), locale(requested),
          typesTried(0), typeFallback(FALSE),
          bundle(NULL), collations(NULL), data(NULL) {
    type[0] = 0;
    defaultType[0] = 0;
    if(U_FAILURE(errorCode)) { return; }

    // Canonicalize the locale ID: Ignore all irrelevant keywords.
    const char *baseName = locale.getBaseName();
    if(uprv_strcmp(locale.getName(), baseName) != 0) {
        locale = Locale(baseName);

        // Fetch the collation type from the locale ID.
        int32_t typeLength = requested.getKeywordValue("collation",
                type, UPRV_LENGTHOF(type) - 1, errorCode);
        if(U_FAILURE(errorCode)) {
            errorCode = U_ILLEGAL_ARGUMENT_ERROR;
            return;
        }
        type[typeLength] = 0;  // in case of U_NOT_TERMINATED_WARNING
        if(typeLength == 0) {
            // No collation type.
        } else if(uprv_stricmp(type, "default") == 0) {
            // Ignore "default" (case-insensitive).
            type[0] = 0;
        } else {
            // Copy the collation type.
            T_CString_toLowerCase(type);
            locale.setKeywordValue("collation", type, errorCode);
        }
    }
}

CollationLoader::~CollationLoader() {
    ures_close(data);
    ures_close(collations);
    ures_close(bundle);
}

const CollationCacheEntry *
CollationLoader::createCacheEntry(UErrorCode &errorCode) {
    // This is a linear lookup and fallback flow turned into a state machine.
    // Most local variables have been turned into instance fields.
    // In a cache miss, cache.get() calls CacheKey::createObject(),
    // which means that we progress via recursion.
    // loadFromCollations() will recurse to itself as well for collation type fallback.
    if(bundle == NULL) {
        return loadFromLocale(errorCode);
    } else if(collations == NULL) {
        return loadFromBundle(errorCode);
    } else if(data == NULL) {
        return loadFromCollations(errorCode);
    } else {
        return loadFromData(errorCode);
    }
}

const CollationCacheEntry *
CollationLoader::loadFromLocale(UErrorCode &errorCode) {
    if(U_FAILURE(errorCode)) { return NULL; }
    U_ASSERT(bundle == NULL);
    bundle = ures_openNoDefault(U_ICUDATA_COLL, locale.getBaseName(), &errorCode);
    if(errorCode == U_MISSING_RESOURCE_ERROR) {
        errorCode = U_USING_DEFAULT_WARNING;

        // Have to add that ref that we promise.
        rootEntry->addRef();
        return rootEntry;
    }
    Locale requestedLocale(locale);
    const char *vLocale = ures_getLocaleByType(bundle, ULOC_ACTUAL_LOCALE, &errorCode);
    if(U_FAILURE(errorCode)) { return NULL; }
    locale = validLocale = Locale(vLocale);  // no type until loadFromCollations()
    if(type[0] != 0) {
        locale.setKeywordValue("collation", type, errorCode);
    }
    if(locale != requestedLocale) {
        return getCacheEntry(errorCode);
    } else {
        return loadFromBundle(errorCode);
    }
}

const CollationCacheEntry *
CollationLoader::loadFromBundle(UErrorCode &errorCode) {
    if(U_FAILURE(errorCode)) { return NULL; }
    U_ASSERT(collations == NULL);
    // There are zero or more tailorings in the collations table.
    collations = ures_getByKey(bundle, "collations", NULL, &errorCode);
    if(errorCode == U_MISSING_RESOURCE_ERROR) {
        errorCode = U_USING_DEFAULT_WARNING;
        // Return the root tailoring with the validLocale, without collation type.
        return makeCacheEntryFromRoot(validLocale, errorCode);
    }
    if(U_FAILURE(errorCode)) { return NULL; }

    // Fetch the default type from the data.
    {
        UErrorCode internalErrorCode = U_ZERO_ERROR;
        LocalUResourceBundlePointer def(
                ures_getByKeyWithFallback(collations, "default", NULL, &internalErrorCode));
        int32_t length;
        const UChar *s = ures_getString(def.getAlias(), &length, &internalErrorCode);
        if(U_SUCCESS(internalErrorCode) && 0 < length && length < UPRV_LENGTHOF(defaultType)) {
            u_UCharsToChars(s, defaultType, length + 1);
        } else {
            uprv_strcpy(defaultType, "standard");
        }
    }

    // Record which collation types we have looked for already,
    // so that we do not deadlock in the cache.
    //
    // If there is no explicit type, then we look in the cache
    // for the entry with the default type.
    // If the explicit type is the default type, then we do not look in the cache
    // for the entry with an empty type.
    // Otherwise, two concurrent requests with opposite fallbacks would deadlock each other.
    // Also, it is easier to always enter the next method with a non-empty type.
    if(type[0] == 0) {
        uprv_strcpy(type, defaultType);
        typesTried |= TRIED_DEFAULT;
        if(uprv_strcmp(type, "search") == 0) {
            typesTried |= TRIED_SEARCH;
        }
        if(uprv_strcmp(type, "standard") == 0) {
            typesTried |= TRIED_STANDARD;
        }
        locale.setKeywordValue("collation", type, errorCode);
        return getCacheEntry(errorCode);
    } else {
        if(uprv_strcmp(type, defaultType) == 0) {
            typesTried |= TRIED_DEFAULT;
        }
        if(uprv_strcmp(type, "search") == 0) {
            typesTried |= TRIED_SEARCH;
        }
        if(uprv_strcmp(type, "standard") == 0) {
            typesTried |= TRIED_STANDARD;
        }
        return loadFromCollations(errorCode);
    }
}

const CollationCacheEntry *
CollationLoader::loadFromCollations(UErrorCode &errorCode) {
    if(U_FAILURE(errorCode)) { return NULL; }
    U_ASSERT(data == NULL);
    // Load the collations/type tailoring, with type fallback.
    LocalUResourceBundlePointer localData(
            ures_getByKeyWithFallback(collations, type, NULL, &errorCode));
    int32_t typeLength = static_cast<int32_t>(uprv_strlen(type));
    if(errorCode == U_MISSING_RESOURCE_ERROR) {
        errorCode = U_USING_DEFAULT_WARNING;
        typeFallback = TRUE;
        if((typesTried & TRIED_SEARCH) == 0 &&
                typeLength > 6 && uprv_strncmp(type, "search", 6) == 0) {
            // fall back from something like "searchjl" to "search"
            typesTried |= TRIED_SEARCH;
            type[6] = 0;
        } else if((typesTried & TRIED_DEFAULT) == 0) {
            // fall back to the default type
            typesTried |= TRIED_DEFAULT;
            uprv_strcpy(type, defaultType);
        } else if((typesTried & TRIED_STANDARD) == 0) {
            // fall back to the "standard" type
            typesTried |= TRIED_STANDARD;
            uprv_strcpy(type, "standard");
        } else {
            // Return the root tailoring with the validLocale, without collation type.
            return makeCacheEntryFromRoot(validLocale, errorCode);
        }
        locale.setKeywordValue("collation", type, errorCode);
        return getCacheEntry(errorCode);
    }
    if(U_FAILURE(errorCode)) { return NULL; }

    data = localData.orphan();
    const char *actualLocale = ures_getLocaleByType(data, ULOC_ACTUAL_LOCALE, &errorCode);
    if(U_FAILURE(errorCode)) { return NULL; }
    const char *vLocale = validLocale.getBaseName();
    UBool actualAndValidLocalesAreDifferent = Locale(actualLocale) != Locale(vLocale);

    // Set the collation types on the informational locales,
    // except when they match the default types (for brevity and backwards compatibility).
    // For the valid locale, suppress the default type.
    if(uprv_strcmp(type, defaultType) != 0) {
        validLocale.setKeywordValue("collation", type, errorCode);
        if(U_FAILURE(errorCode)) { return NULL; }
    }

    // Is this the same as the root collator? If so, then use that instead.
    if((*actualLocale == 0 || uprv_strcmp(actualLocale, "root") == 0) &&
            uprv_strcmp(type, "standard") == 0) {
        if(typeFallback) {
            errorCode = U_USING_DEFAULT_WARNING;
        }
        return makeCacheEntryFromRoot(validLocale, errorCode);
    }

    locale = Locale(actualLocale);
    if(actualAndValidLocalesAreDifferent) {
        locale.setKeywordValue("collation", type, errorCode);
        const CollationCacheEntry *entry = getCacheEntry(errorCode);
        return makeCacheEntry(validLocale, entry, errorCode);
    } else {
        return loadFromData(errorCode);
    }
}

const CollationCacheEntry *
CollationLoader::loadFromData(UErrorCode &errorCode) {
    if(U_FAILURE(errorCode)) { return NULL; }
    LocalPointer<CollationTailoring> t(new CollationTailoring(rootEntry->tailoring->settings));
    if(t.isNull() || t->isBogus()) {
        errorCode = U_MEMORY_ALLOCATION_ERROR;
        return NULL;
    }

    // deserialize
    LocalUResourceBundlePointer binary(ures_getByKey(data, "%%CollationBin", NULL, &errorCode));
    // Note: U_MISSING_RESOURCE_ERROR --> The old code built from rules if available
    // but that created undesirable dependencies.
    int32_t length;
    const uint8_t *inBytes = ures_getBinary(binary.getAlias(), &length, &errorCode);
    CollationDataReader::read(rootEntry->tailoring, inBytes, length, *t, errorCode);
    // Note: U_COLLATOR_VERSION_MISMATCH --> The old code built from rules if available
    // but that created undesirable dependencies.
    if(U_FAILURE(errorCode)) { return NULL; }

    // Try to fetch the optional rules string.
    {
        UErrorCode internalErrorCode = U_ZERO_ERROR;
        int32_t len;
        const UChar *s = ures_getStringByKey(data, "Sequence", &len,
                                             &internalErrorCode);
        if(U_SUCCESS(internalErrorCode)) {
            t->rules.setTo(TRUE, s, len);
        }
    }

    const char *actualLocale = locale.getBaseName();  // without type
    const char *vLocale = validLocale.getBaseName();
    UBool actualAndValidLocalesAreDifferent = Locale(actualLocale) != Locale(vLocale);

    // For the actual locale, suppress the default type *according to the actual locale*.
    // For example, zh has default=pinyin and contains all of the Chinese tailorings.
    // zh_Hant has default=stroke but has no other data.
    // For the valid locale "zh_Hant" we need to suppress stroke.
    // For the actual locale "zh" we need to suppress pinyin instead.
    if(actualAndValidLocalesAreDifferent) {
        // Opening a bundle for the actual locale should always succeed.
        LocalUResourceBundlePointer actualBundle(
                ures_open(U_ICUDATA_COLL, actualLocale, &errorCode));
        if(U_FAILURE(errorCode)) { return NULL; }
        UErrorCode internalErrorCode = U_ZERO_ERROR;
        LocalUResourceBundlePointer def(
                ures_getByKeyWithFallback(actualBundle.getAlias(), "collations/default", NULL,
                                          &internalErrorCode));
        int32_t len;
        const UChar *s = ures_getString(def.getAlias(), &len, &internalErrorCode);
        if(U_SUCCESS(internalErrorCode) && len < UPRV_LENGTHOF(defaultType)) {
            u_UCharsToChars(s, defaultType, len + 1);
        } else {
            uprv_strcpy(defaultType, "standard");
        }
    }
    t->actualLocale = locale;
    if(uprv_strcmp(type, defaultType) != 0) {
        t->actualLocale.setKeywordValue("collation", type, errorCode);
    } else if(uprv_strcmp(locale.getName(), locale.getBaseName()) != 0) {
        // Remove the collation keyword if it was set.
        t->actualLocale.setKeywordValue("collation", NULL, errorCode);
    }
    if(U_FAILURE(errorCode)) { return NULL; }

    if(typeFallback) {
        errorCode = U_USING_DEFAULT_WARNING;
    }
    t->bundle = bundle;
    bundle = NULL;
    const CollationCacheEntry *entry = new CollationCacheEntry(validLocale, t.getAlias());
    if(entry == NULL) {
        errorCode = U_MEMORY_ALLOCATION_ERROR;
        return nullptr;
    } else {
        t.orphan();
    }
    // Have to add that reference that we promise.
    entry->addRef();
    return entry;
}

const CollationCacheEntry *
CollationLoader::getCacheEntry(UErrorCode &errorCode) {
    LocaleCacheKey<CollationCacheEntry> key(locale);
    const CollationCacheEntry *entry = NULL;
    cache->get(key, this, entry, errorCode);
    return entry;
}

const CollationCacheEntry *
CollationLoader::makeCacheEntryFromRoot(
        const Locale &/*loc*/,
        UErrorCode &errorCode) const {
    if (U_FAILURE(errorCode)) {
        return NULL;
    }
    rootEntry->addRef();
    return makeCacheEntry(validLocale, rootEntry, errorCode);
}

const CollationCacheEntry *
CollationLoader::makeCacheEntry(
        const Locale &loc,
        const CollationCacheEntry *entryFromCache,
        UErrorCode &errorCode) {
    if(U_FAILURE(errorCode) || loc == entryFromCache->validLocale) {
        return entryFromCache;
    }
    CollationCacheEntry *entry = new CollationCacheEntry(loc, entryFromCache->tailoring);
    if(entry == NULL) {
        errorCode = U_MEMORY_ALLOCATION_ERROR;
        entryFromCache->removeRef();
        return NULL;
    }
    entry->addRef();
    entryFromCache->removeRef();
    return entry;
}

U_NAMESPACE_END

U_NAMESPACE_USE

U_CAPI UCollator*
ucol_open(const char *loc,
          UErrorCode *status)
{
    UTRACE_ENTRY_OC(UTRACE_UCOL_OPEN);
    UTRACE_DATA1(UTRACE_INFO, "locale = \"%s\"", loc);
    UCollator *result = NULL;

    Collator *coll = Collator::createInstance(loc, *status);
    if(U_SUCCESS(*status)) {
        result = coll->toUCollator();
    }
    UTRACE_EXIT_PTR_STATUS(result, *status);
    return result;
}


U_CAPI int32_t U_EXPORT2
ucol_getDisplayName(    const    char        *objLoc,
                    const    char        *dispLoc,
                    UChar             *result,
                    int32_t         resultLength,
                    UErrorCode        *status)
{
    if(U_FAILURE(*status)) return -1;
    UnicodeString dst;
    if(!(result==NULL && resultLength==0)) {
        // NULL destination for pure preflighting: empty dummy string
        // otherwise, alias the destination buffer
        dst.setTo(result, 0, resultLength);
    }
    Collator::getDisplayName(Locale(objLoc), Locale(dispLoc), dst);
    return dst.extract(result, resultLength, *status);
}

U_CAPI const char* U_EXPORT2
ucol_getAvailable(int32_t index)
{
    int32_t count = 0;
    const Locale *loc = Collator::getAvailableLocales(count);
    if (loc != NULL && index < count) {
        return loc[index].getName();
    }
    return NULL;
}

U_CAPI int32_t U_EXPORT2
ucol_countAvailable()
{
    int32_t count = 0;
    Collator::getAvailableLocales(count);
    return count;
}

#if !UCONFIG_NO_SERVICE
U_CAPI UEnumeration* U_EXPORT2
ucol_openAvailableLocales(UErrorCode *status) {
    // This is a wrapper over Collator::getAvailableLocales()
    if (U_FAILURE(*status)) {
        return NULL;
    }
    StringEnumeration *s = icu::Collator::getAvailableLocales();
    if (s == NULL) {
        *status = U_MEMORY_ALLOCATION_ERROR;
        return NULL;
    }
    return uenum_openFromStringEnumeration(s, status);
}
#endif

// Note: KEYWORDS[0] != RESOURCE_NAME - alan

static const char RESOURCE_NAME[] = "collations";

static const char* const KEYWORDS[] = { "collation" };

#define KEYWORD_COUNT UPRV_LENGTHOF(KEYWORDS)

U_CAPI UEnumeration* U_EXPORT2
ucol_getKeywords(UErrorCode *status) {
    UEnumeration *result = NULL;
    if (U_SUCCESS(*status)) {
        return uenum_openCharStringsEnumeration(KEYWORDS, KEYWORD_COUNT, status);
    }
    return result;
}

U_CAPI UEnumeration* U_EXPORT2
ucol_getKeywordValues(const char *keyword, UErrorCode *status) {
    if (U_FAILURE(*status)) {
        return NULL;
    }
    // hard-coded to accept exactly one collation keyword
    // modify if additional collation keyword is added later
    if (keyword==NULL || uprv_strcmp(keyword, KEYWORDS[0])!=0)
    {
        *status = U_ILLEGAL_ARGUMENT_ERROR;
        return NULL;
    }
    return ures_getKeywordValues(U_ICUDATA_COLL, RESOURCE_NAME, status);
}

static const UEnumeration defaultKeywordValues = {
    NULL,
    NULL,
    ulist_close_keyword_values_iterator,
    ulist_count_keyword_values,
    uenum_unextDefault,
    ulist_next_keyword_value,
    ulist_reset_keyword_values_iterator
};

namespace {

struct KeywordsSink : public ResourceSink {
public:
    KeywordsSink(UErrorCode &errorCode) :
            values(ulist_createEmptyList(&errorCode)), hasDefault(FALSE) {}
    virtual ~KeywordsSink();

    virtual void put(const char *key, ResourceValue &value, UBool /*noFallback*/,
                     UErrorCode &errorCode) {
        if (U_FAILURE(errorCode)) { return; }
        ResourceTable collations = value.getTable(errorCode);
        for (int32_t i = 0; collations.getKeyAndValue(i, key, value); ++i) {
            UResType type = value.getType();
            if (type == URES_STRING) {
                if (!hasDefault && uprv_strcmp(key, "default") == 0) {
                    CharString defcoll;
                    defcoll.appendInvariantChars(value.getUnicodeString(errorCode), errorCode);
                    if (U_SUCCESS(errorCode) && !defcoll.isEmpty()) {
                        char *ownedDefault = uprv_strdup(defcoll.data());
                        if (ownedDefault == NULL) {
                            errorCode = U_MEMORY_ALLOCATION_ERROR;
                            return;
                        }
                        ulist_removeString(values, defcoll.data());
                        ulist_addItemBeginList(values, ownedDefault, TRUE, &errorCode);
                        hasDefault = TRUE;
                    }
                }
            } else if (type == URES_TABLE && uprv_strncmp(key, "private-", 8) != 0) {
                if (!ulist_containsString(values, key, (int32_t)uprv_strlen(key))) {
                    ulist_addItemEndList(values, key, FALSE, &errorCode);
                }
            }
            if (U_FAILURE(errorCode)) { return; }
        }
    }

    UList *values;
    UBool hasDefault;
};

KeywordsSink::~KeywordsSink() {
    ulist_deleteList(values);
}

}  // namespace

U_CAPI UEnumeration* U_EXPORT2
ucol_getKeywordValuesForLocale(const char* /*key*/, const char* locale,
                               UBool /*commonlyUsed*/, UErrorCode* status) {
    // Note: The parameter commonlyUsed is not used.
    // The switch is in the method signature for consistency
    // with other locale services.

    // Read available collation values from collation bundles.
    LocalUResourceBundlePointer bundle(ures_open(U_ICUDATA_COLL, locale, status));
    KeywordsSink sink(*status);
    ures_getAllItemsWithFallback(bundle.getAlias(), RESOURCE_NAME, sink, *status);
    if (U_FAILURE(*status)) { return NULL; }

    UEnumeration *en = (UEnumeration *)uprv_malloc(sizeof(UEnumeration));
    if (en == NULL) {
        *status = U_MEMORY_ALLOCATION_ERROR;
        return NULL;
    }
    memcpy(en, &defaultKeywordValues, sizeof(UEnumeration));
    ulist_resetList(sink.values);  // Initialize the iterator.
    en->context = sink.values;
    sink.values = NULL;  // Avoid deletion in the sink destructor.
    return en;
}

U_CAPI int32_t U_EXPORT2
ucol_getFunctionalEquivalent(char* result, int32_t resultCapacity,
                             const char* keyword, const char* locale,
                             UBool* isAvailable, UErrorCode* status)
{
    // N.B.: Resource name is "collations" but keyword is "collation"
    return ures_getFunctionalEquivalent(result, resultCapacity, U_ICUDATA_COLL,
        "collations", keyword, locale,
        isAvailable, TRUE, status);
}

#endif /* #if !UCONFIG_NO_COLLATION */
