/*
 * Copyright 2011 Google Inc.
 *
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 */

#include "include/private/SkAssert.h"
#include "include/private/SkDebug.h"
#include "include/private/SkFeatures.h"
#include "include/private/SkMalloc.h"

#include <algorithm>
#include <cstddef>
#include <cstdlib>
#include <limits>

#if defined(SK_BUILD_FOR_MAC) || defined(SK_BUILD_FOR_IOS)
#include <malloc/malloc.h>
#elif defined(SK_BUILD_FOR_ANDROID) || defined(SK_BUILD_FOR_UNIX)
#include <malloc.h>
#elif defined(SK_BUILD_FOR_WIN)
#include <malloc.h>
#endif

#if defined(SK_DEBUG) && defined(SK_BUILD_FOR_WIN)
#include <intrin.h>
// This is a super stable value and setting it here avoids pulling in all of windows.h.
#ifndef FAST_FAIL_FATAL_APP_EXIT
#define FAST_FAIL_FATAL_APP_EXIT              7
#endif
#endif

#ifdef SK_BUILD_FOR_ANDROID_FRAMEWORK
    #define SK_DEBUGFAILF(fmt, ...) SK_ABORT(fmt, __VA_ARGS__)
#else
    #define SK_DEBUGFAILF(fmt, ...) SkASSERT((SkDebugf(fmt"\n", __VA_ARGS__), false))
#endif

static inline void sk_out_of_memory(size_t size) {
    SK_DEBUGFAILF("sk_out_of_memory (asked for %zu bytes)",
                  size);
#if defined(SK_BUILD_FOR_AFL_FUZZ)
    exit(1);
#else
    abort();
#endif
}

static inline void* throw_on_failure(size_t size, void* p) {
    if (size > 0 && p == nullptr) {
        // If we've got a nullptr here, the only reason we should have failed is running out of RAM.
        sk_out_of_memory(size);
    }
    return p;
}

void sk_abort_no_print() {
#if defined(SK_DEBUG) && defined(SK_BUILD_FOR_WIN)
    __fastfail(FAST_FAIL_FATAL_APP_EXIT);
#elif defined(__clang__)
    __builtin_trap();
#else
    abort();
#endif
}

void sk_out_of_memory(void) {
    SkDEBUGFAIL("sk_out_of_memory");
#if defined(SK_BUILD_FOR_AFL_FUZZ)
    exit(1);
#else
    abort();
#endif
}

void* sk_realloc_throw(void* addr, size_t size) {
    if (size == 0) {
        sk_free(addr);
        return nullptr;
    }
    return throw_on_failure(size, realloc(addr, size));
}

void sk_free(void* p) {
    // The guard here produces a performance improvement across many tests, and many platforms.
    // Removing the check was tried in skia cl 588037.
    if (p != nullptr) {
        free(p);
    }
}

void* sk_malloc_flags(size_t size, unsigned flags) {
    void* p;
    if (flags & SK_MALLOC_ZERO_INITIALIZE) {
        p = calloc(size, 1);
    } else {
#if defined(SK_BUILD_FOR_ANDROID_FRAMEWORK) && defined(__BIONIC__)
        /* TODO: After b/169449588 is fixed, we will want to change this to restore
         *       original behavior instead of always disabling the flag.
         * TODO: After b/158870657 is fixed and scudo is used globally, we can assert when an
         *       an error is returned.
         */
        // malloc() generally doesn't initialize its memory and that's a huge security hole,
        // so Android has replaced its malloc() with one that zeros memory,
        // but that's a huge performance hit for HWUI, so turn it back off again.
        (void)mallopt(M_THREAD_DISABLE_MEM_INIT, 1);
#endif
        p = malloc(size);
#if defined(SK_BUILD_FOR_ANDROID_FRAMEWORK) && defined(__BIONIC__)
        (void)mallopt(M_THREAD_DISABLE_MEM_INIT, 0);
#endif
    }
    if (flags & SK_MALLOC_THROW) {
        return throw_on_failure(size, p);
    } else {
        return p;
    }
}

size_t sk_malloc_good_size(size_t size) {
    // Use the OS specific calls to find the actual capacity.
    #if defined(SK_BUILD_FOR_MAC) || defined(SK_BUILD_FOR_IOS)
        // Apple provides malloc_good_size
        return std::max(malloc_good_size(size), size);
    #else
        // Other platforms do not provide malloc_good_size, so pick a reasonable implementation.

        // Round up to a nice size. If > 32K align to 4K boundary else up to max_align_t. The > 32K
        // heuristic is from the JEMalloc behavior (see SkArenaAlloc for history).
        static constexpr size_t kMinAlign = alignof(std::max_align_t); // likely 8 or 16
        static constexpr size_t kMaxAlign = 1 << 12; // 4k
        static constexpr size_t kMaxAlignLimit = 1 << 15; // 32k
        size_t mask = (size > kMaxAlignLimit ? kMaxAlign : kMinAlign) - 1;

        if (size > std::numeric_limits<size_t>::max() - mask) {
            // Aligning would overflow, just return the original requested size
            return size;
        } else {
            return (size + mask) & ~mask;
        }
    #endif
}
