14514f5e3Sopenharmony_ci/*
24514f5e3Sopenharmony_ci * Copyright (c) 2021 Huawei Device Co., Ltd.
34514f5e3Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License");
44514f5e3Sopenharmony_ci * you may not use this file except in compliance with the License.
54514f5e3Sopenharmony_ci * You may obtain a copy of the License at
64514f5e3Sopenharmony_ci *
74514f5e3Sopenharmony_ci *     http://www.apache.org/licenses/LICENSE-2.0
84514f5e3Sopenharmony_ci *
94514f5e3Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software
104514f5e3Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS,
114514f5e3Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
124514f5e3Sopenharmony_ci * See the License for the specific language governing permissions and
134514f5e3Sopenharmony_ci * limitations under the License.
144514f5e3Sopenharmony_ci */
154514f5e3Sopenharmony_ci
164514f5e3Sopenharmony_ci#include "ecmascript/mem/c_string.h"
174514f5e3Sopenharmony_ci
184514f5e3Sopenharmony_ci#include <cmath>
194514f5e3Sopenharmony_ci#include <cstdlib>
204514f5e3Sopenharmony_ci
214514f5e3Sopenharmony_ci#include "ecmascript/ecma_string-inl.h"
224514f5e3Sopenharmony_ci#include "ecmascript/js_symbol.h"
234514f5e3Sopenharmony_ci
244514f5e3Sopenharmony_cinamespace panda::ecmascript {
254514f5e3Sopenharmony_cilong CStringToL(const CString &str)
264514f5e3Sopenharmony_ci{
274514f5e3Sopenharmony_ci    char *endPtr = nullptr;
284514f5e3Sopenharmony_ci    int64_t result = std::strtol(str.c_str(), &endPtr, BASE);
294514f5e3Sopenharmony_ci    ASSERT(!(result == 0 && str.c_str() == endPtr) && "CString argument is not long int");
304514f5e3Sopenharmony_ci    return result;
314514f5e3Sopenharmony_ci}
324514f5e3Sopenharmony_ci
334514f5e3Sopenharmony_ciint64_t CStringToLL(const CString &str)
344514f5e3Sopenharmony_ci{
354514f5e3Sopenharmony_ci    char *endPtr = nullptr;
364514f5e3Sopenharmony_ci    int64_t result = std::strtoll(str.c_str(), &endPtr, BASE);
374514f5e3Sopenharmony_ci    ASSERT(!(result == 0 && str.c_str() == endPtr) && "CString argument is not long long int");
384514f5e3Sopenharmony_ci    return result;
394514f5e3Sopenharmony_ci}
404514f5e3Sopenharmony_ci
414514f5e3Sopenharmony_ciuint64_t CStringToULL(const CString &str)
424514f5e3Sopenharmony_ci{
434514f5e3Sopenharmony_ci    char *endPtr = nullptr;
444514f5e3Sopenharmony_ci    uint64_t result = std::strtoull(str.c_str(), &endPtr, BASE);
454514f5e3Sopenharmony_ci    ASSERT(!(result == 0 && str.c_str() == endPtr) && "CString argument is not unsigned long long int");
464514f5e3Sopenharmony_ci    return result;
474514f5e3Sopenharmony_ci}
484514f5e3Sopenharmony_ci
494514f5e3Sopenharmony_cifloat CStringToF(const CString &str)
504514f5e3Sopenharmony_ci{
514514f5e3Sopenharmony_ci    char *endPtr = nullptr;
524514f5e3Sopenharmony_ci    float result = std::strtof(str.c_str(), &endPtr);
534514f5e3Sopenharmony_ci    ASSERT(result != HUGE_VALF && "CString argument is not float");
544514f5e3Sopenharmony_ci    ASSERT(!(result == 0 && str.c_str() == endPtr) && "CString argument is not float");
554514f5e3Sopenharmony_ci    return result;
564514f5e3Sopenharmony_ci}
574514f5e3Sopenharmony_ci
584514f5e3Sopenharmony_cidouble CStringToD(const CString &str)
594514f5e3Sopenharmony_ci{
604514f5e3Sopenharmony_ci    char *endPtr = nullptr;
614514f5e3Sopenharmony_ci    double result = std::strtod(str.c_str(), &endPtr);
624514f5e3Sopenharmony_ci    ASSERT(result != HUGE_VALF && "CString argument is not double");
634514f5e3Sopenharmony_ci    ASSERT(!(result == 0 && str.c_str() == endPtr) && "CString argument is not double");
644514f5e3Sopenharmony_ci    return result;
654514f5e3Sopenharmony_ci}
664514f5e3Sopenharmony_ci
674514f5e3Sopenharmony_citemplate<class T>
684514f5e3Sopenharmony_ciCString ConvertToString(T sp)
694514f5e3Sopenharmony_ci{
704514f5e3Sopenharmony_ci    CString res;
714514f5e3Sopenharmony_ci    res.reserve(sp.size());
724514f5e3Sopenharmony_ci
734514f5e3Sopenharmony_ci    // Also support ascii that great than 127, so using unsigned char here
744514f5e3Sopenharmony_ci    constexpr size_t maxChar = std::numeric_limits<unsigned char>::max();
754514f5e3Sopenharmony_ci
764514f5e3Sopenharmony_ci    for (const auto &c : sp) {
774514f5e3Sopenharmony_ci        if (c > maxChar) {
784514f5e3Sopenharmony_ci            return "";
794514f5e3Sopenharmony_ci        }
804514f5e3Sopenharmony_ci        res.push_back(c);
814514f5e3Sopenharmony_ci    }
824514f5e3Sopenharmony_ci
834514f5e3Sopenharmony_ci    return res;
844514f5e3Sopenharmony_ci}
854514f5e3Sopenharmony_ci
864514f5e3Sopenharmony_ci// NB! the following function need additional mem allocation, don't use when unnecessary!
874514f5e3Sopenharmony_ciCString ConvertToString(const std::string &str)
884514f5e3Sopenharmony_ci{
894514f5e3Sopenharmony_ci    CString res;
904514f5e3Sopenharmony_ci    res.reserve(str.size());
914514f5e3Sopenharmony_ci    for (auto c : str) {
924514f5e3Sopenharmony_ci        res.push_back(c);
934514f5e3Sopenharmony_ci    }
944514f5e3Sopenharmony_ci    return res;
954514f5e3Sopenharmony_ci}
964514f5e3Sopenharmony_ci
974514f5e3Sopenharmony_ciCString ConvertToString(const EcmaString *s, StringConvertedUsage usage, bool cesu8)
984514f5e3Sopenharmony_ci{
994514f5e3Sopenharmony_ci    if (s == nullptr) {
1004514f5e3Sopenharmony_ci        return CString("");
1014514f5e3Sopenharmony_ci    }
1024514f5e3Sopenharmony_ci    return EcmaStringAccessor(const_cast<EcmaString *>(s)).ToCString(usage, cesu8);
1034514f5e3Sopenharmony_ci}
1044514f5e3Sopenharmony_ci
1054514f5e3Sopenharmony_ciCString ConvertToString(JSTaggedValue key)
1064514f5e3Sopenharmony_ci{
1074514f5e3Sopenharmony_ci    ASSERT(key.IsStringOrSymbol());
1084514f5e3Sopenharmony_ci    if (key.IsString()) {
1094514f5e3Sopenharmony_ci        return ConvertToString(EcmaString::ConstCast(key.GetTaggedObject()));
1104514f5e3Sopenharmony_ci    }
1114514f5e3Sopenharmony_ci
1124514f5e3Sopenharmony_ci    ecmascript::JSTaggedValue desc = JSSymbol::Cast(key.GetTaggedObject())->GetDescription();
1134514f5e3Sopenharmony_ci    if (desc.IsUndefined()) {
1144514f5e3Sopenharmony_ci        return CString("Symbol()");
1154514f5e3Sopenharmony_ci    }
1164514f5e3Sopenharmony_ci
1174514f5e3Sopenharmony_ci    return ConvertToString(EcmaString::ConstCast(desc.GetTaggedObject()));
1184514f5e3Sopenharmony_ci}
1194514f5e3Sopenharmony_ci
1204514f5e3Sopenharmony_cistd::string ConvertToStdString(const CString &str)
1214514f5e3Sopenharmony_ci{
1224514f5e3Sopenharmony_ci    std::string res;
1234514f5e3Sopenharmony_ci    res.reserve(str.size());
1244514f5e3Sopenharmony_ci    for (auto c : str) {
1254514f5e3Sopenharmony_ci        res.push_back(c);
1264514f5e3Sopenharmony_ci    }
1274514f5e3Sopenharmony_ci    return res;
1284514f5e3Sopenharmony_ci}
1294514f5e3Sopenharmony_ci}  // namespace panda::ecmascript
130