/*
 * Copyright (C) 2011 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#ifndef _H_UTILS
#define _H_UTILS

#ifdef _WIN32

#define _CRT_SECURE_NO_WARNINGS 1

#include <direct.h>
#include <stdio.h>
#include <stdarg.h>
#include <string.h>
#include <windows.h>

// VS vs MINGW specific includes
#ifdef USE_VS_CRT
    #include <crtdbg.h>     // for _ASSERT
#else
    #define _ASSERT(x)      // undef
#endif

extern bool gIsDebug;
extern bool gIsConsole;

// An array that knows its own size. Not dynamically resizable.
template <class T> class CArray {
    T* mPtr;
    int mSize;
public:
    explicit CArray(int size) {
        mSize = size;
        mPtr = new T[size];
    }

    ~CArray() {
        if (mPtr != NULL) {
            delete[] mPtr;
            mPtr = NULL;
        }
        mSize = 0;
    }

    T& operator[](int i) {
        _ASSERT(i >= 0 && i < mSize);
        return mPtr[i];
    }

    int size() const {
        return mSize;
    }
};

// A simple string class wrapper.
class CString {
protected:
    char *mStr;
public:
    CString()                              { mStr = NULL; }
    CString(const CString &str)            { mStr = NULL; set(str.mStr); }
    explicit CString(const char *str)      { mStr = NULL; set(str); }
    CString(const char *start, size_t length) { mStr = NULL; set(start, length); }

    CString& operator=(const CString &str) {
        return set(str.cstr());
    }

    CString& set(const char *str) {
        if (str != mStr) {
            _free();
            if (str != NULL) {
                mStr = _strdup(str);
            }
        }
        return *this;
    }

    CString& set(const char *start, size_t length) {
        _free();
        if (start != NULL) {
            mStr = (char *)malloc(length + 1);
            strncpy(mStr, start, length);
            mStr[length] = 0;
        }
        return *this;
    }

    CString& setv(const char *str, va_list ap) {
        _free();
        // _vscprintf(str, ap) is only available with the MSVCRT, not MinGW.
        // Instead we'll iterate till we have enough space to generate the string.
        size_t len = strlen(str) + 1024;
        mStr = (char *)malloc(len);
        strcpy(mStr, str); // provide a default in case vsnprintf totally fails
        for (int guard = 0; guard < 10; guard++) {
            int ret = vsnprintf(mStr, len, str, ap);
            if (ret == -1) {
                // Some implementations don't give the proper size needed
                // so double the space and try again.
                len *= 2;
            } else if (ret >= len) {
                len = ret + 1;
            } else {
                // There was enough space to write.
                break;
            }
            mStr = (char *)realloc((void *)mStr, len);
            strcpy(mStr, str); // provide a default in case vsnprintf totally fails
        }
        return *this;
    }

    CString& setf(const char *str, ...) {
        _free();
        va_list ap;
        va_start(ap, str);
        setv(str, ap);
        va_end(ap);
        return *this;
    }

    virtual ~CString() { _free(); }

    // Returns the C string owned by this CString. It will be
    // invalid as soon as this CString is deleted or out of scope.
    const char * cstr() const {
        return mStr;
    }

    bool isEmpty() const {
        return mStr == NULL || *mStr == 0;
    }

    size_t length() const {
        return mStr == NULL ? 0 : strlen(mStr);
    }

    CString& add(const char *str) {
        if (mStr == NULL) {
            set(str);
        } else {
            mStr = (char *)realloc((void *)mStr, strlen(mStr) + strlen(str) + 1);
            strcat(mStr, str);
        }
        return *this;
    }

    CString& add(const char *str, int length) {
        if (mStr == NULL) {
            set(str, length);
        } else {
            size_t l1 = strlen(mStr);
            mStr = (char *)realloc((void *)mStr, l1 + length + 1);
            strncpy(mStr + l1, str, length);
            mStr[l1 + length] = 0;
        }
        return *this;
    }

    CArray<CString> * split(char sep) const {
        if (mStr == NULL) {
            return new CArray<CString>(0);
        }
        const char *last = NULL;
        int n = 0;
        for (const char *s = mStr; *s; s++) {
            if (*s == sep && s != mStr && (last == NULL || s > last+1)) {
                n++;
                last = s;
            }
        }

        CArray<CString> *result = new CArray<CString>(n);
        last = NULL;
        n = 0;
        for (const char *s = mStr; *s; s++) {
            if (*s == sep) {
                if (s != mStr && (last == NULL || s > last+1)) {
                    const char *start = last ? last : mStr;
                    (*result)[n++].set(start, s-start);
                }
                last = s+1;
            }
        }

        return result;
    }

    // Sets the string to the message matching Win32 GetLastError.
    // If message is non-null, it is prepended to the last error string.
    CString& setLastWin32Error(const char *message) {
        DWORD err = GetLastError();
        LPSTR errStr;
        if (FormatMessageA(FORMAT_MESSAGE_ALLOCATE_BUFFER | /* dwFlags */
                          FORMAT_MESSAGE_FROM_SYSTEM,
                          NULL,                             /* lpSource */
                          err,                              /* dwMessageId */
                          0,                                /* dwLanguageId */
                          (LPSTR)&errStr,                   /* lpBuffer */
                          0,                                /* nSize */
                          NULL) != 0) {                     /* va_list args */
            if (message == NULL) {
                setf("[%d] %s", err, errStr);
            } else {
                setf("%s[%d] %s", message, err, errStr);
            }
            LocalFree(errStr);
        }
        return *this;
    }

private:
    void _free() {
        if (mStr != NULL) {
            free((void *)mStr);
            mStr = NULL;
        }
    }

};

// A simple path class wrapper.
class CPath : public CString {
public:
    CPath()                              : CString()    { }
    CPath(const CString &str)            : CString(str) { }
    CPath(const CPath &str)              : CString(str) { }
    explicit CPath(const char *str)      : CString(str) { }
    CPath(const char *start, int length) : CString(start, length) { }

    CPath& operator=(const CPath &str) {
        set(str.cstr());
        return *this;
    }

    // Appends a path segment, adding a \ as necessary.
    CPath& addPath(const CString &s) {
        return addPath(s.cstr());
    }

    // Appends a path segment, adding a \ as necessary.
    CPath& addPath(const char *s) {
        _ASSERT(s != NULL);
        if (s != NULL && s[0] != 0) {
            size_t n = length();
            if (n > 0 && s[0] != '\\' && mStr[n-1] != '\\') add("\\");
            add(s);
        }
        return *this;
    }

    // Returns true if file exist and is not a directory.
    // There's no garantee we have rights to access it.
    bool fileExists() const {
        if (mStr == NULL) return false;
        DWORD attribs = GetFileAttributesA(mStr);
        return attribs != INVALID_FILE_ATTRIBUTES &&
             !(attribs & FILE_ATTRIBUTE_DIRECTORY);
    }

    // Returns true if file exist and is a directory.
    // There's no garantee we have rights to access it.
    bool dirExists() const {
        if (mStr == NULL) return false;
        DWORD attribs = GetFileAttributesA(mStr);
        return attribs != INVALID_FILE_ATTRIBUTES &&
              (attribs & FILE_ATTRIBUTE_DIRECTORY) != 0;
    }

    // Returns a copy of the directory portion of the path, if any
    CPath dirName() const {
        CPath result;
        if (mStr != NULL) {
            char *pos = strrchr(mStr, '\\');
            if (pos != NULL) {
                result.set(mStr, pos - mStr);
            }
        }
        return result;
    }

    // Returns a pointer to the baseName part of the path.
    // It becomes invalid if the path changes.
    const char * baseName() const {
        if (mStr != NULL) {
            char *pos = strrchr(mStr, '\\');
            if (pos != NULL) {
                return pos + 1;
            }
        }
        return NULL;
    }

    // If the path ends with the given searchName, replace in-place by the new name
    void replaceName(const char *searchName, const char* newName) {
        if (mStr == NULL) return;
        size_t n = length();
        size_t sn = strlen(searchName);
        if (n < sn) return;
        // if mStr ends with searchName
        if (strcmp(mStr + n - sn, searchName) == 0) {
            size_t sn2 = strlen(newName);
            if (sn2 > sn) {
                mStr = (char *)realloc((void *)mStr, n + sn2 - sn + 1);
            }
            strcpy(mStr + n - sn, newName);
            mStr[n + sn2 - sn] = 0;
        }
    }

    // Returns a copy of this path as a DOS short path in the destination.
    // Returns true if the Win32 getShortPathName method worked.
    // In case of error, returns false and does not change the destination.
    // It's OK to invoke this->toShortPath(this).
    bool toShortPath(CPath *dest) {
        const char *longPath = mStr;
        if (mStr == NULL) return false;

        DWORD lenShort = (DWORD)strlen(longPath) + 1; // GetShortPathName deals with DWORDs
        char * shortPath = (char *)malloc(lenShort);

        DWORD length = GetShortPathName(longPath, shortPath, lenShort);
        if (length > lenShort) {
            // The buffer wasn't big enough, this is the size to use.
            free(shortPath);
            lenShort = length;
            shortPath = (char *)malloc(length);
            length = GetShortPathName(longPath, shortPath, lenShort);
        }

        if (length != 0) dest->set(shortPath);

        free(shortPath);
        return length != 0;
    }
};

// Displays a message in an ok+info dialog box.
void msgBox(const char* text, ...);

// Displays GetLastError prefixed with a description in an error dialog box
void displayLastError(const char *description, ...);

// Executes the command line. Does not wait for the program to finish.
// The return code is from CreateProcess (0 means failure), not the running app.
int execNoWait(const char *app, const char *params, const char *workDir);

// Executes command, waits for completion and returns exit code.
// As indicated in MSDN for CreateProcess, callers should double-quote the program name
// e.g. cmd="\"c:\program files\myapp.exe\" arg1 arg2";
int execWait(const char *cmd);

bool getModuleDir(CPath *outDir);

#endif /* _WIN32 */
#endif /* _H_UTILS */
