// Copyright 2014 PDFium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
 
// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com

#include "../../include/fxcrt/fx_ext.h"
#include "fxcrt_posix.h"
#if _FXM_PLATFORM_ == _FXM_PLATFORM_LINUX_ || _FXM_PLATFORM_ == _FXM_PLATFORM_APPLE_ || _FXM_PLATFORM_ == _FXM_PLATFORM_ANDROID_
IFXCRT_FileAccess* FXCRT_FileAccess_Create()
{
    return new CFXCRT_FileAccess_Posix;
}
void FXCRT_Posix_GetFileMode(FX_DWORD dwModes, int32_t &nFlags, int32_t &nMasks)
{
    nFlags = O_BINARY | O_LARGEFILE;
    if (dwModes & FX_FILEMODE_ReadOnly) {
        nFlags |= O_RDONLY;
        nMasks = 0;
    } else {
        nFlags |= O_RDWR | O_CREAT;
        if (dwModes & FX_FILEMODE_Truncate) {
            nFlags |= O_TRUNC;
        }
        nMasks = S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH;
    }
}
CFXCRT_FileAccess_Posix::CFXCRT_FileAccess_Posix()
    : m_nFD(-1)
{
}
CFXCRT_FileAccess_Posix::~CFXCRT_FileAccess_Posix()
{
    Close();
}
FX_BOOL CFXCRT_FileAccess_Posix::Open(const CFX_ByteStringC& fileName, FX_DWORD dwMode)
{
    if (m_nFD > -1) {
        return FALSE;
    }
    int32_t nFlags, nMasks;
    FXCRT_Posix_GetFileMode(dwMode, nFlags, nMasks);
    m_nFD = open(fileName.GetCStr(), nFlags, nMasks);
    return m_nFD > -1;
}
FX_BOOL CFXCRT_FileAccess_Posix::Open(const CFX_WideStringC& fileName, FX_DWORD dwMode)
{
    return Open(FX_UTF8Encode(fileName), dwMode);
}
void CFXCRT_FileAccess_Posix::Close()
{
    if (m_nFD < 0) {
        return;
    }
    close(m_nFD);
    m_nFD = -1;
}
void CFXCRT_FileAccess_Posix::Release()
{
    delete this;
}
FX_FILESIZE CFXCRT_FileAccess_Posix::GetSize() const
{
    if (m_nFD < 0) {
        return 0;
    }
    struct stat s;
    FXSYS_memset(&s, 0, sizeof(s));
    fstat(m_nFD, &s);
    return s.st_size;
}
FX_FILESIZE CFXCRT_FileAccess_Posix::GetPosition() const
{
    if (m_nFD < 0) {
        return (FX_FILESIZE) - 1;
    }
    return lseek(m_nFD, 0, SEEK_CUR);
}
FX_FILESIZE CFXCRT_FileAccess_Posix::SetPosition(FX_FILESIZE pos)
{
    if (m_nFD < 0) {
        return (FX_FILESIZE) - 1;
    }
    return lseek(m_nFD, pos, SEEK_SET);
}
size_t CFXCRT_FileAccess_Posix::Read(void* pBuffer, size_t szBuffer)
{
    if (m_nFD < 0) {
        return 0;
    }
    return read(m_nFD, pBuffer, szBuffer);
}
size_t CFXCRT_FileAccess_Posix::Write(const void* pBuffer, size_t szBuffer)
{
    if (m_nFD < 0) {
        return 0;
    }
    return write(m_nFD, pBuffer, szBuffer);
}
size_t CFXCRT_FileAccess_Posix::ReadPos(void* pBuffer, size_t szBuffer, FX_FILESIZE pos)
{
    if (m_nFD < 0) {
        return 0;
    }
    if (pos >= GetSize()) {
        return 0;
    }
    if (SetPosition(pos) == (FX_FILESIZE) - 1) {
        return 0;
    }
    return Read(pBuffer, szBuffer);
}
size_t CFXCRT_FileAccess_Posix::WritePos(const void* pBuffer, size_t szBuffer, FX_FILESIZE pos)
{
    if (m_nFD < 0) {
        return 0;
    }
    if (SetPosition(pos) == (FX_FILESIZE) - 1) {
        return 0;
    }
    return Write(pBuffer, szBuffer);
}
FX_BOOL CFXCRT_FileAccess_Posix::Flush()
{
    if (m_nFD < 0) {
        return FALSE;
    }
    return fsync(m_nFD) > -1;
}
FX_BOOL CFXCRT_FileAccess_Posix::Truncate(FX_FILESIZE szFile)
{
    if (m_nFD < 0) {
        return FALSE;
    }
    return !ftruncate(m_nFD, szFile);
}
FX_BOOL FX_File_Exist(const CFX_ByteStringC& fileName)
{
    return access(fileName.GetCStr(), F_OK) > -1;
}
FX_BOOL FX_File_Exist(const CFX_WideStringC& fileName)
{
    return FX_File_Exist(FX_UTF8Encode(fileName));
}
FX_BOOL FX_File_Delete(const CFX_ByteStringC& fileName)
{
    return remove(fileName.GetCStr()) > -1;
}
FX_BOOL FX_File_Delete(const CFX_WideStringC& fileName)
{
    return FX_File_Delete(FX_UTF8Encode(fileName));
}
FX_BOOL FX_File_Copy(const CFX_ByteStringC& fileNameSrc, const CFX_ByteStringC& fileNameDst)
{
    CFXCRT_FileAccess_Posix src, dst;
    if (!src.Open(fileNameSrc, FX_FILEMODE_ReadOnly)) {
        return FALSE;
    }
    FX_FILESIZE size = src.GetSize();
    if (!size) {
        return FALSE;
    }
    if (!dst.Open(fileNameDst, FX_FILEMODE_Truncate)) {
        return FALSE;
    }
    size_t num = 0;
    uint8_t* pBuffer = FX_Alloc(uint8_t, 32768);
    num = src.Read(pBuffer, 32768);
    while (num) {
        if (dst.Write(pBuffer, num) != num) {
            break;
        }
        num = src.Read(pBuffer, 32768);
    }
    FX_Free(pBuffer);
    return TRUE;
}
FX_BOOL FX_File_Copy(const CFX_WideStringC& fileNameSrc, const CFX_WideStringC& fileNameDst)
{
    return FX_File_Copy(FX_UTF8Encode(fileNameSrc), FX_UTF8Encode(fileNameDst));
}
FX_BOOL FX_File_Move(const CFX_ByteStringC& fileNameSrc, const CFX_ByteStringC& fileNameDst)
{
    return rename(fileNameSrc.GetCStr(), fileNameDst.GetCStr());
}
FX_BOOL FX_File_Move(const CFX_WideStringC& fileNameSrc, const CFX_WideStringC& fileNameDst)
{
    return FX_File_Move(FX_UTF8Encode(fileNameSrc), FX_UTF8Encode(fileNameDst));
}
#endif
