NodeType FetchFileStatus(const AnyString& filename, yuint64& size, yint64& lastModified, bool followSymLink) { size = 0u; lastModified = 0; return (YUNI_LIKELY(not filename.empty())) ? Stat(filename, size, lastModified, followSymLink) : IO::typeUnknown; }
Cursor Transaction::prepare(const AnyString& stmt) { assert(!(!pChannel)); // the adapter ::yn_dbi_adapter& adapter = pChannel->adapter; if (YUNI_UNLIKELY(nullHandle == pTxHandle)) { if (errNone != pChannel->begin(pTxHandle)) return Cursor(adapter, nullptr); } // query handle void* handle = nullptr; if (YUNI_LIKELY(not stmt.empty() and adapter.dbh)) { assert(adapter.query_new != NULL and "invalid adapter query_new"); assert(adapter.query_ref_acquire != NULL and "invalid adapter query_ref_acquire"); assert(adapter.query_ref_release != NULL and "invalid adapter query_ref_release"); adapter.query_new(&handle, adapter.dbh, stmt.c_str(), stmt.size()); } return Cursor(adapter, handle); }
NodeType TypeOf(const AnyString& filename, bool followSymLink) { yuint64 size; // useless yint64 lastModified; return (YUNI_LIKELY(not filename.empty())) ? Stat(filename, size, lastModified, followSymLink) : IO::typeUnknown; }
File::File(const AnyString& filePath): pFormat(nullptr) { if (filePath.empty()) return; # if LIBAVFORMAT_VERSION_MAJOR < 53 if (::av_open_input_file(&pFormat, filePath.c_str(), nullptr, 0, nullptr)) # else if (::avformat_open_input(&pFormat, filePath.c_str(), nullptr, nullptr)) # endif // LIBAVFORMAT_VERSION_MAJOR < 53 { pFormat = nullptr; return; } // After opening, we must search for the stream information because not // all formats will have it in stream headers (eg. system MPEG streams) # if LIBAVFORMAT_VERSION_MAJOR < 53 if (::av_find_stream_info(pFormat) < 0) # else if (::avformat_find_stream_info(pFormat, nullptr) < 0) # endif // LIBAVFORMAT_VERSION_MAJOR < 53 { # if LIBAVFORMAT_VERSION_MAJOR < 53 ::av_close_input_file(pFormat); # else ::avformat_close_input(&pFormat); # endif // LIBAVFORMAT_VERSION_MAJOR < 53 pFormat = nullptr; return; } }
bool Size(const AnyString& filename, uint64& value) { struct stat results; if (not filename.empty() && stat(filename.c_str(), &results) == 0) { value = (uint64) results.st_size; return true; } value = 0u; return false; }
Yuni::IO::NodeType TypeOf(const AnyString& filename) { if (filename.empty()) return Yuni::IO::typeUnknown; # ifdef YUNI_OS_WINDOWS const char* p = filename.c_str(); unsigned int len = filename.size(); if (p[len - 1] == '\\' or p[len - 1] == '/') { if (!--len) { # ifdef YUNI_OS_WINDOWS return Yuni::IO::typeUnknown; # else // On Unixes, `/` is a valid folder return Yuni::IO::typeFolder; # endif } } // Driver letters if (len == 2 and p[1] == ':') return Yuni::IO::typeFolder; String norm; Yuni::IO::Normalize(norm, AnyString(p, len)); // Conversion into wchar_t Private::WString<true> wstr(norm); if (wstr.empty()) return Yuni::IO::typeUnknown; WIN32_FILE_ATTRIBUTE_DATA infoFile; if (!GetFileAttributesExW(wstr.c_str(), GetFileExInfoStandard, &infoFile)) return Yuni::IO::typeUnknown; return ((infoFile.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) != 0) ? Yuni::IO::typeFolder : Yuni::IO::typeFile; # else // WINDOWS struct stat s; if (stat(filename.c_str(), &s) != 0) return Yuni::IO::typeUnknown; return (S_ISDIR(s.st_mode)) ? Yuni::IO::typeFolder : Yuni::IO::typeFile; # endif }
bool Create(const AnyString& path, uint mode) { if (not path.empty() and not Yuni::IO::Exists(path)) { # ifdef YUNI_OS_WINDOWS // `mode` is not used on Windows (void) mode; return WindowsMake(path); # else return UnixMake(path, mode); # endif } return true; }
Yuni::IO::Error Delete(const AnyString& filename) { // DeleteFile is actually a macro and will be replaced by DeleteFileW // with Visual Studio. Consequently we can not use the word DeleteFile..... if (filename.empty()) return Yuni::IO::errUnknown; # ifndef YUNI_OS_WINDOWS return (unlink(filename.c_str())) ? Yuni::IO::errUnknown : Yuni::IO::errNone; # else const char* const p = filename.c_str(); uint len = filename.size(); if (p[len - 1] == '\\' or p[len - 1] == '/') --len; // Driver letters if (len == 2 and p[1] == ':') return Yuni::IO::errBadFilename; String norm; Yuni::IO::Normalize(norm, AnyString(p, len)); // Conversion into wchar_t WString wstr(norm, true); if (wstr.empty()) return Yuni::IO::errUnknown; wstr.replace('/', '\\'); return (DeleteFileW(wstr.c_str())) ? Yuni::IO::errNone : Yuni::IO::errUnknown; # endif }
static bool DecodeURLQuery(KeyValueStore& params, const AnyString& query) { // note: mongoose does not provide the fragment here, so we don't have // to check it // Some tests are already done before calling this method assert(not query.empty()); String key; // temporary string for parameters handling uint offset = 0; uint start = 0; AnyString value; do { offset = query.find_first_of("=&", offset); if (offset >= query.size()) { // ignoring fields with empty value (using default) break; } if (query[offset] == '=') { key.assign(query, offset - start, start); if (key.empty()) // malformed url. aborting return false; ++offset; // FIXME !!!! & are not properly handled !!!!!!!!!!!! uint ampersand = offset; ampersand = query.find('&', ampersand); if (ampersand >= query.size()) { value.adapt(query, query.size() - offset, offset); ampersand = query.size(); } else value.adapt(query, ampersand - offset, offset); if (not value.empty()) { KeyValueStore::iterator i = params.find(key); if (i != params.end()) { // the item has been found ! params[key] = value; } } offset = ampersand; } else { // ignoring fields with empty value (using default) } // updating offsets start = ++offset; } while (true); return true; }
void Program::commandLine(AnyString cmd) { // remove all whitespaces cmd.trim(); auto envptr = pEnv; // keeping a reference to the current env if (!envptr) { envptr = std::make_shared<ProcessSharedInfo>(); pEnv = envptr; } ProcessSharedInfo& env = *envptr; MutexLocker locker(env.mutex); env.executable.clear(); env.arguments.clear(); if (cmd.empty()) return; String* str = &env.executable; char instring = '\0'; const AnyString::null_iterator end = cmd.utf8end(); for (AnyString::const_utf8iterator i = cmd.utf8begin(); i != end; ++i) { char c = *i; switch (c) { default: { *str += i.value(); break; } case '"': [[fallthrough]]; case '\'': { if (instring == '\0') { instring = c; } else { if (instring == c) instring = '\0'; else *str += c; } break; } case '\\': { ++i; if (YUNI_UNLIKELY(i == end)) return; c = *i; switch (c) { case 'n': (*str) += '\n'; break; case 't': (*str) += '\t'; break; case 'r': (*str) += '\r'; break; case 'b': (*str) += '\b'; break; case 'f': (*str) += '\f'; break; case 'v': (*str) += '\v'; break; case '0': (*str) += '\0'; break; case 'e': [[fallthrough]]; case 'a': [[fallthrough]]; case 'E': break; default: (*str) << '\\' << c; break; } break; } case ' ': [[fallthrough]]; case '\t': { if (instring == '\0') { if (not str->empty()) { env.arguments.push_back(nullptr); str = &(env.arguments.back()); } } else *str += c; break; } } } }
void WString::prepareWString(const AnyString& string, bool uncprefix) { if (string.empty()) { if (uncprefix) { pSize = 4; pWString = (wchar_t*)::realloc(pWString, sizeof(wchar_t) * 5); pWString[0] = L'\\'; pWString[1] = L'\\'; pWString[2] = L'?'; pWString[3] = L'\\'; pWString[4] = L'\0'; } else clear(); return; } if (string.size() > INT_MAX) { clear(); return; } // Offset according to the presence of the UNC prefix const uint offset = (not uncprefix) ? 0 : 4; #ifdef YUNI_OS_WINDOWS { // Allocate and convert the C-String. Several iterations may be required // for allocating enough room for the conversion. const int sizeRequired = MultiByteToWideChar(CP_UTF8, 0, string.c_str(), string.size(), nullptr, 0); if (sizeRequired <= 0) { clear(); return; } pSize = sizeRequired + offset; pWString = (wchar_t*) realloc(pWString, sizeof(wchar_t) * (pSize + 1)); if (nullptr == pWString) // Impossible to allocate the buffer. Aborting. { clear(); return; } // Converting into Wide String const int n = MultiByteToWideChar(CP_UTF8, 0, string.c_str(), static_cast<int>(string.size()), pWString + offset, static_cast<int>(pSize - offset)); if (n != sizeRequired) { assert(false and "most likely an error"); clear(); return; } } #else { const char* wcstr = string.c_str(); mbstate_t state; memset (&state, '\0', sizeof (state)); size_t sizeRequired = mbsnrtowcs(nullptr, &wcstr, string.size(), 0, &state); if (0 == sizeRequired or (size_t) -1 == sizeRequired) { clear(); return; } pSize = sizeRequired + offset; pWString = (wchar_t*) realloc(pWString, sizeof(wchar_t) * (pSize + 1)); if (nullptr == pWString) // Impossible to allocate the buffer. Aborting. { clear(); return; } memset (&state, '\0', sizeof (state)); size_t written = mbsnrtowcs(pWString + offset, &wcstr, string.size(), pSize - offset, &state); if (0 == written or (size_t) -1 == written) { clear(); return; } } #endif // prepend the Windows UNC prefix if (uncprefix) { pWString[0] = L'\\'; pWString[1] = L'\\'; pWString[2] = L'?'; pWString[3] = L'\\'; } // always ensure that the string is zero terminated pWString[pSize] = L'\0'; }
bool Resize(const AnyString& filename, uint64_t size) { if (not filename.empty()) { if (size < std::numeric_limits<off_t>::max()) { #ifndef YUNI_OS_WINDOWS { assert((filename.c_str())[filename.size()] == '\0'); #ifdef YUNI_OS_MAC int fd = open(filename.c_str(), O_WRONLY|O_CREAT, 0644); #else int fd = open(filename.c_str(), O_WRONLY|O_CREAT|O_LARGEFILE, 0644); #endif if (fd != -1) { bool success = (0 == ftruncate(fd, static_cast<off_t>(size))); close(fd); return success; } } #else { WString wstr(filename, true); if (not wstr.empty()) { HANDLE hndl = CreateFileW(wstr.c_str(), GENERIC_WRITE, FILE_SHARE_WRITE, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL); if (hndl) { LARGE_INTEGER li; li.QuadPart = size; DWORD dwPtr = SetFilePointer(hndl, li.LowPart, &li.HighPart, FILE_BEGIN); if (dwPtr != INVALID_SET_FILE_POINTER) SetEndOfFile(hndl); CloseHandle(hndl); return true; } } } #endif } } return false; }