/*
 * Copyright (C) 2009 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.
 */

#include <stdlib.h>
#include "../include/utf16char.h"

namespace ime_pinyin {

#ifdef __cplusplus
extern "C" {
#endif

  char16* utf16_strtok(char16 *utf16_str, size_t *token_size,
                       char16 **utf16_str_next) {
    if (NULL == utf16_str || NULL == token_size || NULL == utf16_str_next) {
      return NULL;
    }

    // Skip the splitters
    size_t pos = 0;
    while ((char16)' ' == utf16_str[pos] || (char16)'\n' == utf16_str[pos]
           || (char16)'\t' == utf16_str[pos])
      pos++;

    utf16_str += pos;
    pos = 0;

    while ((char16)'\0' != utf16_str[pos] && (char16)' ' != utf16_str[pos]
           && (char16)'\n' != utf16_str[pos]
           && (char16)'\t' != utf16_str[pos]) {
      pos++;
    }

    char16 *ret_val = utf16_str;
    if ((char16)'\0' == utf16_str[pos]) {
      *utf16_str_next = NULL;
      if (0 == pos)
        return NULL;
    } else {
      *utf16_str_next = utf16_str + pos + 1;
    }

    utf16_str[pos] = (char16)'\0';
    *token_size = pos;

    return ret_val;
  }

  int utf16_atoi(const char16 *utf16_str) {
    if (NULL == utf16_str)
      return 0;

    int value = 0;
    int sign = 1;
    size_t pos = 0;

    if ((char16)'-' == utf16_str[pos]) {
      sign = -1;
      pos++;
    }

    while ((char16)'0' <=  utf16_str[pos] &&
           (char16)'9' >= utf16_str[pos]) {
      value = value * 10 + static_cast<int>(utf16_str[pos] - (char16)'0');
      pos++;
    }

    return value*sign;
  }

  float utf16_atof(const char16 *utf16_str) {
    // A temporary implemetation.
    char char8[256];
    if (utf16_strlen(utf16_str) >= 256) return 0;

    utf16_strcpy_tochar(char8, utf16_str);
    return atof(char8);
  }

  size_t utf16_strlen(const char16 *utf16_str) {
    if (NULL == utf16_str)
      return 0;

    size_t size = 0;
    while ((char16)'\0' != utf16_str[size])
      size++;
    return size;
  }

  int utf16_strcmp(const char16* str1, const char16* str2) {
    size_t pos = 0;
    while (str1[pos] == str2[pos] && (char16)'\0' != str1[pos])
      pos++;

    return static_cast<int>(str1[pos]) - static_cast<int>(str2[pos]);
  }

  int utf16_strncmp(const char16 *str1, const char16 *str2, size_t size) {
    size_t pos = 0;
    while (pos < size && str1[pos] == str2[pos] && (char16)'\0' != str1[pos])
      pos++;

    if (pos == size)
      return 0;

    return static_cast<int>(str1[pos]) - static_cast<int>(str2[pos]);
  }

  // we do not consider overlapping
  char16* utf16_strcpy(char16 *dst, const char16 *src) {
    if (NULL == src || NULL == dst)
      return NULL;

    char16* cp = dst;

    while ((char16)'\0' != *src) {
      *cp = *src;
      cp++;
      src++;
    }

    *cp = *src;

    return dst;
  }

  char16* utf16_strncpy(char16 *dst, const char16 *src, size_t size) {
    if (NULL == src || NULL == dst || 0 == size)
      return NULL;

    if (src == dst)
      return dst;

    char16* cp = dst;

    if (dst < src || (dst > src && dst >= src + size)) {
      while (size-- && (*cp++ = *src++))
        ;
    } else {
      cp += size - 1;
      src += size - 1;
      while (size-- && (*cp-- == *src--))
        ;
    }
    return dst;
  }

  // We do not handle complicated cases like overlapping, because in this
  // codebase, it is not necessary.
  char* utf16_strcpy_tochar(char *dst, const char16 *src) {
    if (NULL == src || NULL == dst)
      return NULL;

    char* cp = dst;

    while ((char16)'\0' != *src) {
      *cp = static_cast<char>(*src);
      cp++;
      src++;
    }
    *cp = *src;

    return dst;
  }

#ifdef __cplusplus
}
#endif
}  // namespace ime_pinyin
